% \iffalse % feynmf.dtx - Feynman diagrams with METAFONT for LaTeX(2e)
% Copyright (C) 1989, 1990, 1992-1995 by Thorsten.Ohl@Physik.TH-Darmstadt.de
% /home/sources/ohl/tex/thotex/feynmf/feynmf.dtx,v 1.10 1995/02/18 16:42:18 ohl Exp
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% Feynmf is free software; you can redistribute it and/or modify it
% under the terms of the GNU General Public License as published by 
% the Free Software Foundation; either version 2, or (at your option)
% any later version.
%
% Feynmf is distributed in the hope that it will be useful, but
% WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program; if not, write to the Free Software
% Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% \fi
%
%% \CheckSum{553}
%% \CharacterTable
%%  {Upper-case    \A\B\C\D\E\F\G\H\I\J\K\L\M\N\O\P\Q\R\S\T\U\V\W\X\Y\Z
%%   Lower-case    \a\b\c\d\e\f\g\h\i\j\k\l\m\n\o\p\q\r\s\t\u\v\w\x\y\z
%%   Digits        \0\1\2\3\4\5\6\7\8\9
%%   Exclamation   \!     Double quote  \"     Hash (number) \#
%%   Dollar        \$     Percent       \%     Ampersand     \&
%%   Acute accent  \'     Left paren    \(     Right paren   \)
%%   Asterisk      \*     Plus          \+     Comma         \,
%%   Minus         \-     Point         \.     Solidus       \/
%%   Colon         \:     Semicolon     \;     Less than     \<
%%   Equals        \=     Greater than  \>     Question mark \?
%%   Commercial at \@     Left bracket  \[     Backslash     \\
%%   Right bracket \]     Circumflex    \^     Underscore    \_
%%   Grave accent  \`     Left brace    \{     Vertical bar  \|
%%   Right brace   \}     Tilde         \~}
%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% \MakeShortVerb{\|}
%
% \title{%
%   \FMF: \\
%   Drawing Feynman Diagrams \\
%   with \LaTeX{} and \MF}
%
% \author{%
%   Thorsten Ohl\thanks{e-mail:
%     {\tt Thorsten.Ohl@Physik.TH-Darmstadt.de}}\\
%   \hfil \\
%   Technische Hochschule Darmstadt \\
%   Schlo\ss gartenstr. 9 \\
%   D-64289 Darmstadt \\
%   Germany}
%
% \maketitle
% \begin{abstract}
%   \FMF{} is a \LaTeX{} package for easy drawing of professional
%   quality Feynman diagrams with \MF.  \FMF{} lays out most
%   diagrams satisfactorily from the structure of the graph without
%   any need for manual intervention.  Nevertheless all the power of
%   \MF{} is available for the most obscure cases.
% \end{abstract}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section*{Copying}
%
% \FMF{} is free software; you can redistribute it and/or modify it
% under the terms of the GNU General Public License as published by 
% the Free Software Foundation; either version 2, or (at your option)
% any later version.
%
% \FMF{} is distributed in the hope that it will be useful, but
% \emph{without any warranty}; without even the implied warranty of
% \emph{merchantability} or \emph{fitness for a particular purpose}.
% See the GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program; if not, write to the Free Software
% Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \tableofcontents
% \unitlength=1mm
% \begin{fmffile}{fmfsampl}
% \def\bottomfraction{0}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section{Introduction}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Purpose and scope}
%
% In recent years, \TeX\footnote{\TeX{} is a trademark of the American
%   Mathematical Society.}~\cite{TeX}
% and \LaTeX\footnote{\LaTeX{} might be a trademark of Addison Wesley
%   Publishing Company.}~\cite{LaTeX}
% have revolutionized the way
% we share information in theoretical physics (and other areas).  Not
% only does \TeX{} provide typographical capabilities, which transcend
% those of commercial ``wordprocessors'' substantially, \TeX{} documents
% are also completely portable.  Since implementations are available
% on essentially all computers in use in the community, documents can
% be shared without the usual restrictions of proprietary data
% formats.  This has enabled us to collaborate on papers with
% colleagues on the other side of the globe, to replace the mailing of
% hard copy preprints by electronic transmission and to submit these
% papers electronically to the publisher.
%
% This portability comes with a price, though.  \TeX{} (and \LaTeX)
% do not address the issue of graphical information, apart from the
% rudimentary (but very useful) capabilities of the \LaTeX{} |picture|
% environment and similar
% packages~\cite{LaTeX-Companion}, which provide line drawings like
% the one in figure~\ref{fig:flow}.  As an de facto standard for the
% inclusion of more complex graphics has emerged the inclusion of
% PostScript~\footnote{PostScript is a trademark of Adobe Systems
%   Inc.} 
% files.  The complete document can then
% be printed on any PostScript device.
%
% Still there are areas, where complementary approaches seem worth
% pursuing.  In particular this is the case, if the graphical
% information is highly formalized, like the case at hand.  Feynman
% diagrams are specified by their topology and the type of particles
% connecting the vertices.  Thus a given diagram can be reproduced
% from a very concise specification, if the software is able to choose
% a reasonable layout (semi-)automatically.
%
% \MF\footnote{\MF{} is a trademark of Addison Wesley Publishing
%   Company.}~\cite{MF}
% and \MP\footnote{John Hobby's \MP{} is a modified version of \MF{}
%   which generates (encapsulated) PostScript output.  \MP{} can be
%   build trivially on top of the \texttt{web2c} version of \TeX{} and
%   \MF{} for UNIX.  Ports to other systems should be
%   simple.}~\cite{MetaPost}
% appear to be the perfect tool for such a purpose, since
% \begin{enumerate}
%   \item{} \MF{} is part of any (reasonable) \TeX{} installation, thus
%     available to all potential users,
%   \item{} both have very powerful graphics primitivs, which allow high
%     quality output, and
%   \item{} both have builtin linear algebra, which allows us to choose a
%     layout automatically.
% \end{enumerate}
% Still, providing at least the basic interface in \LaTeX{} macros
% seems appropriate for boosting the acceptance among the less
% technically oriented parts of the audience. Thus
% \FMF\footnote{\FMF{} is not a trademark of anybody.}
% was conceived.
%
% \FMF{} supports \MF{} as well as \MP{} (under the names
% \texttt{feynmp.sty} and \texttt{feynmp.mp}).
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Relation to similar packages}
%
% Before we start, a couple of words about some complementary packages
% on the market are in order.  First of all: I failed to do my
% homework and didn't try hard enough to find~\cite{hoenig} in a
% library.  I'm sure that in there is a smarter way of returning
% information from \MF{} to \TeX{}.  Those who don't know the
% literature are doomed to reinvent the wheel.  But this isn't a
% scholarly work and reinventing the wheel was \emph{fun!}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Feynman}
%
% Micheal Levine's |feynman| package~\cite{levine} is
% implemented on top of the standard \LaTeX{} |picture|
% environment~\cite{LaTeX}.  This makes it completely portable (no
% need for a correct \MF{} installation), but it requires manual
% layout and the graphics output is (though very useful) less than
% perfect.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Axodraw}
%
% Jos Vermaseren's |axodraw| package~\cite{axodraw} uses
% |\special|s to access PostScript primitives for drawing diagrams.
% This approach is inherently not portable (though the ubiquity of
% PostScript printers makes this a minor point) but at least as
% flexible as the present one.  It still requires manual layout,
% though.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Mfpic}
%
% Last, but not least, I have to mention  Thomas Leathrum's
% |mfpic|~\cite{mfpic}, which was the main inspiration for moving
% \FMF's user interface from \MF{} to \TeX.  It might not have been
% unreasonable to design and implement \FMF{} as a package on top of
% |mfpic|\footnote{In fact a change in this direction would be rather
%   easy.},
% But closer inspection shows that \FMF{} and |mfpic| are fairly
% orthogonal.  |mfpic| is ideally suited for handling simple graphical
% building blocks in formally unconstrained contexts, a task which will
% be accomplished preferably by direct manual placement of objects.
% \FMF{} on the other hand works in the highly formal context of
% Feynman diagrams (or any other labeled graphs for that matter),
% which can be draw automatically from a \emph{specification}.
%
% It will of course be tempting to add more features from |mfpic|'s
% realm to \FMF{} in the future, but I will try to be conservative in
% that respect.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Historical note}
%
% This code has a rather long history\footnote{Which is a partial
% explanation, if not excuse, for its slightly incoherent structure.}.
% Most of the sections~\ref{sec:mf-basics}, \ref{sec:pictures},
% \ref{sec:shading}, and~\ref{sec:drawing} started in 1989 as
% |feynman.mf|, a library of \MF{} macros for drawing Feynman
% diagrams in my thesis.  The layout had to be chossen completely
% manually, which required a long edit-process-preview cycle and made
% |feynman.mf| awkward to use.
% Nevertheless, it survived for five years without major
% modifications, only slight enhancements had been made.  Early in
% 1994, I became aware of Thomas Leathrum's |mfpic|~\cite{mfpic}.
% This inspired me to shift the user interface from \MF{} to
% \LaTeX, because this allows a smoother blending of the \LaTeX{}
% |picture| environment with \FMF{}.  While doing this and after
% having been taught by Tim Stelzer's and Bill Long's
% \texttt{MADGRAPH}~\cite{madgraph} that minimizing the length of the
% graph gives surprisingly good results for tree graphs\footnote{I had
% thought about this earlier myself, but foolishly discarded the idea.
% I didn't expect such a ``too simple'' method to give esthetically
% pleasing results for loop graphs, which were my main concern.}, I
% added the graph manipulation code in section~\ref{sec:graphs}.
%
% And, of course, \FMF{} is biased towards those kinds of graphs that
% my students, my colleagues and myself have to draw most often.
% Comments for improvements from other areas of physics are welcome.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Projects}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Documented \MF{} Interface}
%
% In a future version, \FMF{} will have a more convenient and
% supported set of macros at the \MF{} level, including more general
% drawing primitives.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Less Formal Graphs}
%
% In addition to the well defined Feynman graphs of perturbation
% theory there are also less formal and more illustrative graphs in
% use. For example the ``quark diagrams'' familiar from papers on
% hadronic weak decays involve curved lines illustrating the formation
% of bound states, etc. Future versions of \FMF{} will provide better
% support for such graphs, without the need for raw \MF{} coding.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Virtual Graphs}
% \label{sec:virtual-pictures}
%
% In a future version, \FMF{} will be able to draw ``virtual''
% graphs, i.e.~graphs which are larger than the current limit enforced
% by numeric overflow at higher resolutions.  This can be implemented
% by calculating the layout of a miniature graph and afterwards
% distributing the full graph among several \MF{} characters.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Conclusion}
%
% It goes without saying that \FMF{} is not perfect.  There are
% cases where using a graphical drawing tool with a mouse will give
% more pleasing results in less time.  But in most cases, \FMF{}
% will give satisfactory results without any fine tuning.  These will
% be reproducible and independent from the computer it is running on.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section{Usage}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Invocation}
%
% Instructing \LaTeX{} to use \FMF{} is as simple as\footnote{As
%   given, this applies to \LaTeX.  But the installation file
%   \texttt{feynmf209.ins} allows to generate special versions 
%   \texttt{feynmf209.sty} and \texttt{feynmp209.sty} which are
%   compatible with the obsolete \LaTeX{} version 2.09.  These files
%   are to be used as documentstyle options.}
% \begin{verbatim}
%   \usepackage{feynmf}
% \end{verbatim}
% and calling \MF{} should not be harder as
% \begin{verbatim}
%   mf '\mode:=localmode; input foobar'
% \end{verbatim}
% where |foobar| is the name of your \MF{} output file and |localmode|
% is your local printer (e.g.~|laserjet|).
% The hard part usually lies in instructing \TeX{} and your favorite
% |dvi|-driver how to find the generated |tfm| and |gf| (resp.~|pk|)
% files.  This is highly system dependent and can be trivial (as in
% the standard UNIX\footnote{UNIX was a trademark of UNIX Systems
%   Laboratory, but is rumored to have been donored to X/Open.}
% \TeX{} installations) or almost impossible (as
% under MVS).  Please consult your local guide or local ``\TeX{}
% Wizards'' on this point.
%
% If you have \MP, then you can use it by placing
% \begin{verbatim}
%   \usepackage[dvips]{feynmp}
% \end{verbatim}
% in your \LaTeX{} source.  Here |dvips| is an option for the
% \LaTeX{} |egraphics| package which is used for including the
% generated PostScript files.  It should be replaced by your local
% supported |dvi| driver.  Calling \MP{} is usually even simpler
% \begin{verbatim}
%   mp foobar
% \end{verbatim}
% since there is no mode to be picked.
%
% Please keep in mind that \FMF{} has been developed for \LaTeXe{} and
% the \LaTeX~2.09 compatibility version will always be a retrofitted
% hack.  I will accept bug reports for the 2.09 version, but I urge
% everybody to move to \LaTeX2e, which is the one and onloy supported
% \LaTeX{} right now.
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \begin{figure}
%   \begin{center}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \setlength{\unitlength}{0.012500in}%
% \begingroup\makeatletter\ifx\SetFigFont\undefined
% \def\x#1#2#3#4#5#6#7\relax{\def\x{#1#2#3#4#5#6}}%
% \expandafter\x\fmtname xxxxxx\relax \def\y{splain}%
% \ifx\x\y   % LaTeX or SliTeX?
% \gdef\SetFigFont#1#2#3{%
%   \ifnum #1<17\tiny\else \ifnum #1<20\small\else
%   \ifnum #1<24\normalsize\else \ifnum #1<29\large\else
%   \ifnum #1<34\Large\else \ifnum #1<41\LARGE\else
%      \huge\fi\fi\fi\fi\fi\fi
%   \csname #3\endcsname}%
% \else
% \gdef\SetFigFont#1#2#3{\begingroup
%   \count@#1\relax \ifnum 25<\count@\count@25\fi
%   \def\x{\endgroup\@setsize\SetFigFont{#2pt}}%
%   \expandafter\x
%     \csname \romannumeral\the\count@ pt\expandafter\endcsname
%     \csname @\romannumeral\the\count@ pt\endcsname
%   \csname #3\endcsname}%
% \fi
% \fi\endgroup
% \begin{picture}(377,400)(3,420)
% \thinlines
% \put( 40,740){\framebox(80,80){}}
% \put( 55,795){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}foo.tex}}}
% \put(280,760){\framebox(60,40){}}
% \put(295,780){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.mf}}}
% \put(160,680){\framebox(60,40){}}
% \put(170,705){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.log}}}
% \put(320,640){\framebox(60,40){}}
% \put(323,664){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.300gf}}}
% \put(100,600){\framebox(60,40){}}
% \put(110,620){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.t1}}}
% \put(180,600){\framebox(60,40){}}
% \put(185,622){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.t2}}}
% \put(260,560){\framebox(60,40){}}
% \put(270,585){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.tfm}}}
% \put( 40,420){\framebox(80,80){}}
% \put( 50,485){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}foo.dvi}}}
% \put(290,463){\oval(130,74)}
% \put(260,470){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}lpr}}}
% \thicklines
% \put(295,760){\vector(-3,-1){106.500}}
% \put(325,760){\vector( 1,-3){ 26.500}}
% \put(310,760){\vector(-1,-4){ 39.118}}
% \multiput(120,780)(11.85185,0.00000){14}{\line( 1, 0){  5.926}}
% \put(280,780){\vector( 1, 0){0}}
% \put( 60,500){\vector( 0,-1){0}}
% \multiput( 60,740)(0.00000,-4.52830){53}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put( 80,500){\vector(-1,-2){0}}
% \multiput(130,600)(-2.00000,-4.00000){25}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put(120,480){\vector(-2,-1){0}}
% \multiput(280,560)(-4.00000,-2.00000){40}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put(210,640){\vector( 1,-4){0}}
% \multiput(200,680)(1.11764,-4.47058){9}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put(129,642){\vector(-4,-3){0}}
% \multiput(180,680)(-3.65714,-2.74286){14}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \thinlines
% \put(120,460){\vector( 1, 0){105}}
% \put(300,560){\vector( 0,-1){ 60}}
% \put(350,640){\vector( 0,-1){145}}
% \thicklines
% \put(105,494){\vector(-1,-1){0}}
% \multiput(211,600)(-3.19697,-3.19697){33}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put(160,790){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}\LaTeX{} \#1}}}
% \put(360,535){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}dvi2xxx}}}
% \put(350,725){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}\MF}}}
% \put(  3,663){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}\LaTeX{} \#2}}}
% \end{picture}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%   \end{center}
%   \caption{Flow of information in a \FMF{} application:  The
%      first \LaTeX{} pass is shown with a dashed line.  The \MF{}
%      pass is shown with the full lines and the second \LaTeX{} pass
%      with dotted lines.  The final dvi translation step is shown with
%      thin lines.}
%   \label{fig:flow}
% \end{figure}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% The flow of information depicted in figure~\ref{fig:flow} looks much
% more complicated than it is.  The important feature is that there a
% two sets of files which can be used to distribute a document:
% \begin{enumerate}
%   \item{} Iff the recipient has a working \MF{} installation
%     (which shouldn't be a problem, except for some impoverished
%     commercial implementations), the document can be typset from the
%     \LaTeX{} source \emph{alone}, by running \LaTeX{}, \MF{}
%     and \LaTeX{} again (the latter step might have to be repeated to
%     get cross references right).
%   \item{} Another possibility (which doesn't require \MF{} on
%     the recipient's side), is to distribute the \LaTeX{} source, the
%     |tfm| and |gf| files (or |pk| files respectively) along with the
%     label files with extension |t|$n$ (where $n$ as an integer).
%     Distributing the \MF{} |log| files is a possible alternative
%     for the latter, but discouraged, because these are prone to be
%     erased accidentally.
% \end{enumerate}
%
% I should add one caveat here: some |dvi| file previewers
% (e.g.~xdvi(1) under UNIX) do \emph{not} reread font information if
% the |tfm| or |pk| files have changed, even though they reread the
% |dvi| file if it has changed.  Thus you have to restart such
% previewers if you have made changes in diagrams to see these changes
% on the screen.
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \begin{figure}
%   \begin{center}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \setlength{\unitlength}{0.012500in}%
% \begingroup\makeatletter\ifx\SetFigFont\undefined
% \def\x#1#2#3#4#5#6#7\relax{\def\x{#1#2#3#4#5#6}}%
% \expandafter\x\fmtname xxxxxx\relax \def\y{splain}%
% \ifx\x\y   % LaTeX or SliTeX?
% \gdef\SetFigFont#1#2#3{%
%   \ifnum #1<17\tiny\else \ifnum #1<20\small\else
%   \ifnum #1<24\normalsize\else \ifnum #1<29\large\else
%   \ifnum #1<34\Large\else \ifnum #1<41\LARGE\else
%      \huge\fi\fi\fi\fi\fi\fi
%   \csname #3\endcsname}%
% \else
% \gdef\SetFigFont#1#2#3{\begingroup
%   \count@#1\relax \ifnum 25<\count@\count@25\fi
%   \def\x{\endgroup\@setsize\SetFigFont{#2pt}}%
%   \expandafter\x
%     \csname \romannumeral\the\count@ pt\expandafter\endcsname
%     \csname @\romannumeral\the\count@ pt\endcsname
%   \csname #3\endcsname}%
% \fi
% \fi\endgroup
% \begin{picture}(357,400)(3,420)
% \thinlines
% \put( 40,740){\framebox(80,80){}}
% \put( 55,795){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}foo.tex}}}
% \put( 40,420){\framebox(80,80){}}
% \put( 50,485){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}foo.dvi}}}
% \put(290,463){\oval(130,74)}
% \put(260,470){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}lpr}}}
% \put(100,640){\framebox(60,40){}}
% \put(110,660){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.t1}}}
% \put(180,640){\framebox(60,40){}}
% \put(185,662){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.t2}}}
% \put(220,580){\framebox(60,40){}}
% \put(230,605){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.1}}}
% \put(300,580){\framebox(60,40){}}
% \put(303,604){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.2}}}
% \put(280,760){\framebox(60,40){}}
% \put(295,780){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{tt}fd.mp}}}
% \thicklines
% \put(325,760){\vector( 0,-1){140}}
% \put(310,760){\vector(-1,-2){ 69}}
% \multiput(120,780)(11.85185,0.00000){14}{\line( 1, 0){  5.926}}
% \put(280,780){\vector( 1, 0){0}}
% \put( 60,500){\vector( 0,-1){0}}
% \multiput( 60,740)(0.00000,-4.52830){53}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put( 83,499){\vector(-1,-3){0}}
% \multiput(130,640)(-1.42424,-4.27273){33}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put(115,486){\vector(-4,-3){0}}
% \multiput(240,580)(-3.56571,-2.67429){35}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \thinlines
% \put(120,460){\vector( 1, 0){105}}
% \put(260,580){\vector( 1,-2){ 40}}
% \thicklines
% \put(104,497){\vector(-3,-4){0}}
% \multiput(211,640)(-2.67900,-3.57200){40}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \thinlines
% \put(345,580){\vector(-1,-2){ 40}}
% \thicklines
% \put(295,760){\vector(-1,-1){ 82}}
% \put(295,760){\vector(-2,-1){164}}
% \put(120,480){\vector(-2,-1){0}}
% \multiput(320,580)(-4.00000,-2.00000){50}{\makebox(0.4444,0.6667){\SetFigFont{10}{12}{rm}.}}
% \put(160,790){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}\LaTeX \#1}}}
% \put(  3,663){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}\LaTeX \#2}}}
% \put(345,520){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}dvips}}}
% \put(340,685){\makebox(0,0)[lb]{\smash{\SetFigFont{12}{14.4}{rm}\MP}}}
% \end{picture}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%   \end{center}
%   \caption{Flow of information in a \FMF{} application if \MP{} is
%      used instead of \MF.}
%   \label{fig:flowp}
% \end{figure}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Basic usage}
%
% The basic features of \FMF{} are (or rather ``should be'')
% available through the \LaTeX{} interface.  Not knowledge of
% \MF{} is necessary.
%
% \DescribeEnv{fmffile}
% Upto 255 characters can be placed into one \MF{} file, they are
% enclosed in a single |fmffile| environment.  The environment
% takes the filename as argument.  Currently \FMF{} does \emph{not}
% check that the 255 character limit per file is not overrun.
% \begin{verbatim}
%   \begin{fmffile}{foobar}
%     ...
%   \end{fmffile}
% \end{verbatim}
% Note that the filename for the \MF{} file given in the argument of
% the |fmffile| environment \emph{must not} be identical to the
% \LaTeX{} source file name, because the \MF{} |.log| would be
% overwritten and \LaTeX{} can no longer access the information in
% this |.log| file.
%
% \DescribeEnv{fmfchar}
% Draw one character and place it here.  Arguments are
% |(|\meta{width}|,|\meta{height}|)| as in:
% \begin{verbatim}
%   \begin{fmfchar}(40,25)
%     ...
%   \end{fmfchar}
% \end{verbatim}
% This environment does \emph{not} support labels, use |fmfchar*| if
% your diagrams contains labels.
%
% \DescribeEnv{fmfchar*}
% Same as |fmfchar|, but enclosed in a |picture| environment of the
% same size and supporting \LaTeX{} labels.
% \begin{verbatim}
%   \begin{fmfchar*}(40,25)
%     ...
%   \end{fmfchar*}
% \end{verbatim}
%
% \DescribeMacro{\fmfleft}
% \DescribeMacro{\fmfright}
% \DescribeMacro{\fmfbottom}
% \DescribeMacro{\fmftop}
% \DescribeMacro{\fmfsurround}
% Positioning of
% external vertices has to done explicitely.  The technical reason is
% that they would otherwise collapse with their neighbors, but
% practical reasons also suggest to give the user full control here.
% |\fmfleft{|\meta{v1}$[$|,|\ldots$]$|}| places the
% vertices in the comma separated list \meta{v1},\ldots
% equidistantly on a smooth path on the left side of the diagram.
% |\fmfright{|\meta{v1}$[$|,|\ldots$]$|}| does the same
% thing on the right.  Similarly |\fmfbottom| and |\fmftop|, while
% |\fmfsurround{|\meta{v1}$[$|,|\ldots$]$|}|
% places its arguments on smooth path
% surrounding the diagram:
% \def\gallerylabels{%
%   \fmfdotn{v}{4}%
%   \fmflabel{$v_1$}{v1}%
%   \fmflabel{$v_2$}{v2}%
%   \fmflabel{$v_3$}{v3}%
%   \fmflabel{$v_4$}{v4}}
% \begin{center}
%   \label{p:galleries}
%   \hfil\\
%   \fbox{\begin{fmfchar*}(15,12)
%     \fmfpen{thick}%
%     \fmfbottomn{v}{4}\gallerylabels
%     \fmfcmd{draw (bottom_gallery);}
%   \end{fmfchar*}}\qquad
%   \fbox{\begin{fmfchar*}(15,12)
%     \fmfpen{thick}%
%     \fmfleftn{v}{4}\gallerylabels
%     \fmfcmd{draw (left_gallery);}
%   \end{fmfchar*}}\qquad
%   \fbox{\begin{fmfchar*}(15,12)
%     \fmfpen{thick}%
%     \fmfsurroundn{v}{7}\fmfdotn{v}{7}%
%     \fmflabel{$v_1$}{v1}\fmflabel{$v_2$}{v2}%
%     \fmflabel{$v_3$}{v3}\fmflabel{$v_4$}{v4}%
%     \fmflabel{$v_5$}{v5}\fmflabel{$v_6$}{v6}%
%     \fmflabel{$v_7$}{v7}%
%     \fmfcmd{draw (surround_gallery);}
%   \end{fmfchar*}}\qquad
%   \fbox{\begin{fmfchar*}(15,12)
%     \fmfpen{thick}%
%     \fmftopn{v}{4}\gallerylabels
%     \fmfcmd{draw (top_gallery);}
%   \end{fmfchar*}}\qquad
%   \fbox{\begin{fmfchar*}(15,12)
%     \fmfpen{thick}%
%     \fmfrightn{v}{4}\gallerylabels
%     \fmfcmd{draw (right_gallery);}
%   \end{fmfchar*}}\\
%   \hfil
% \end{center}
%
% \DescribeMacro{\fmfpen}
% Pick up a pen of the specified size.  |\fmfpen{|\meta{weight}|}|
% is used for changing the weight (i.e.~thickness) of the lines.
% Predefined sizes are |thin| and |thick|.
%
% \def\linesample#1{%
%   \begin{fmfchar}(30,4)
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2}
%     \fmf{#1}{i1,o1}
%   \end{fmfchar}}
% \begin{table}
%   \begin{tabular}{lcll}
%     Name               & Example                       & Parameters  & Aliases  \\\hline
%     |curly|            & \linesample{curly}            & |curly_len| & |gluon|  \\
%     |dbl_curly|        & \linesample{dbl_curly}        & |curly_len| & \\
%     |dashes|           & \linesample{dashes}           & |dash_len|  & \\
%     |dashes_arrow|     & \linesample{dashes_arrow}     & |dash_len|  & |scalar| \\
%     |dbl_dashes|       & \linesample{dbl_dashes}       & |dash_len|  & \\
%     |dbl_dashes_arrow| & \linesample{dbl_dashes_arrow} & |dash_len|  & \\
%     |dots|             & \linesample{dots}             & |dot_len|   & \\
%     |dots_arrow|       & \linesample{dots_arrow}       & |dot_len|   & |ghost|  \\
%     |dbl_dots|         & \linesample{dbl_dots}         & |dot_len|   & \\
%     |dbl_dots_arrow|   & \linesample{dbl_dots_arrow}   & |dot_len|   & \\
%     |phantom|          & \linesample{phantom}          &             & \\
%     |phantom_arrow|    & \linesample{phantom_arrow}    &             & \\
%     |plain|            & \linesample{plain}            &             & |vanilla|\\
%     |plain_arrow|      & \linesample{plain_arrow}      &             & |fermion|,
%                                                                        |electron|,
%                                                                        |quark|  \\
%     |dbl_plain|        & \linesample{dbl_plain}        &             & |double| \\
%     |dbl_plain_arrow|  & \linesample{dbl_plain_arrow}  &             & |double_arrow|,
%                                                                        |heavy|  \\
%     |wiggly|           & \linesample{wiggly}           & |wiggly_len|& |boson|,
%                                                                        |photon| \\
%     |dbl_wiggly|       & \linesample{dbl_wiggly}       & |wiggly_len|&
%   \end{tabular}
%   \caption{Available line styles}
%   \label{tab:line-styles}
% \end{table}
%
% \begin{table}
%   \begin{tabular}{lp{60mm}}
%     Name         & Explanation \\\hline
%     |tension|    & draw a tighter ($>1$) or more loos ($<1$) arc \\
%     |left|       & draw on a halfcircle on the left \\
%     |right|      & draw on a halfcircle on the right \\
%     |straight|   & draw on a straight line \\
%     |label|      & \TeX{} text for labeling the arc \\
%     |label.side| & force placement of the label on the |left| or
%                   |right| \\
%     |label.dist| & place label at a distance |dist| \\
%     |label.pos|  & relative position of the label
%                    (not implemented yet!) \\
%     |decoration.shape|  & shape of decoration
%                           (not implemented yet!) \\
%     |decoration.size|   & size of decoration
%                           (not implemented yet!) \\
%     |decoration.pos|    & relative position of decoration
%                           (not implemented yet!) \\
%     |decoration.filled| & fill, shade or hatch decoration
%                           (not implemented yet!) \\
%     |decoration.angle|  & rotate decoration relative to default
%                           (not implemented yet!)
%   \end{tabular}
%   \caption{Available line options}
%   \label{tab:line-options}
% \end{table}
%
% \DescribeMacro{\fmf}
% This is the the most frequently used macro in \FMF{} applications.
% |\fmf{|\meta{style}\allowbreak
%   $[$|,|\meta{opt}\allowbreak
%   $[$|=|\meta{val}$]$|,|\ldots$]$|}{|\meta{v1}|,|\meta{v2}\allowbreak
%   $[$|,|\ldots$]$|}|
% connects the vertices \textit{v1,v2,\ldots} with a line of style
% \meta{style}, using a set of options \meta{opt} with (optional)
% value \meta{val}.  If a vertex is not
% known yet, it is added to the diagram.  Note that the actual drawing
% is not done immediately, because the positions can only be
% calculated when \emph{all} vertices are known. The currently
% available styles are collected in table~\ref{tab:line-styles}.  Most
% names should be self explanatory
% and are not discussed further.
% The |dashes|, |dots|, |phantom| and |plain| styles can optionally be
% decorated with an arrow as shown above.  All styles, including
% |curly| and |wiggly|, can be doubled.  But arrows are not available
% for the latter two, because esthetically pleasing results can not be
% expected.  The |phantom|
% style is special, because it
% only enters the vertices and does \emph{not} cause a line to be
% drawn.  This is extremely useful for advanced layout features, as
% explained below.
% The supported options are collected in
% table~\ref{tab:line-options}\footnote{%
%   \begin{dubious}
%     One particulary useful further option would be \texttt{smooth},
%     allowing for several lines joined smoothly.  Early
%     experimentation has shown however, that the results are not
%     always what one expects and that there is a lot of room for
%     abuse.
%   \end{dubious}}.
% Note that each of the dot separated components of the options can be
% abbreviated.  For example, |l.d| is equivalent to |label.dist|.  The
% result of ambiguous matches is however undefined.
%
% \begin{table}
%   \begin{tabular}{lp{60mm}}
%     Name                 & Explanation \\\hline
%     |label|              & \TeX{} text for labeling the vertex \\
%     |label.angle|        & force placement of the label at the given
%                            angle from the vertex \\
%     |label.dist|         & place label at a distance |dist| \\
%     |decoration.shape|   & shape of decoration \\
%     |decoration.size|    & size of decoration \\
%     |decoration.filled|  & fill, shade or hatch decoration \\
%     |decoration.angle|   & rotate decoration
%   \end{tabular}
%   \caption{Available vertex options}
%   \label{tab:vertex-options}
% \end{table}
%
% \DescribeMacro{\fmfv}
% Declare vertices with options:
% |\fmfv{|\meta{shape}$[$|=|\meta{val}$]$\allowbreak
%   $[$|,|\meta{opt}\allowbreak
%   $[$|=|\meta{val}$]$|,|\ldots$]$|}{|\meta{v1}\allowbreak
%   $[$|,|\ldots$]$|}|
% This is used for adding labels to a vertex and for specifying other
% decoration.  Supported options are collected in
% table~\ref{tab:vertex-options}.  Here the same abbreviation
% mechanism as above is in effect.  The available |shape|s are listed
% in various filling styles in table~\ref{tab:vertex-shapes}\footnote{%
%   If the variable \texttt{feymfwizard} is \texttt{true} (e.g.~after
%   calling the \texttt{fmfwizard} macro),
%   it is also possible to specify any \MF{} expression that evaluates
%   to a \texttt{path}.  Naturally, this has to used with great care,
%   because strange errors can be triggered by typos!}.
%
% \def\VertexSample#1#2{%
%   \begin{fmfchar}(8,8)
%     \fmfforce{(.5w,.4h)}{c}
%     \fmfv{d.shape=#1,d.filled=#2}{c}
%   \end{fmfchar}}
% \def\VertexSamples#1{%
%   \VertexSample{#1}{-.5} & \VertexSample{#1}{0}
%   & \VertexSample{#1}{.5} & \VertexSample{#1}{1}}
% \begin{table}
%   \begin{center}
%     \begin{tabular}{lcccc}
%                  & |filled=-.5| & |filled=0| & |filled=.5| & |filled=1| \\
%       \hline
%       |circle|   & \VertexSamples{circle} \\
%       |square|   & \VertexSamples{square} \\
%       |triangle| & \VertexSamples{triangle} \\
%       |diamond|  & \VertexSamples{diamond} \\
%       |pentagon| & \VertexSamples{pentagon} \\
%       |hexagon|  & \VertexSamples{hexagon} \\
%       |triagram| & \VertexSamples{triagram} \\
%       |tetragram|& \VertexSamples{tetragram} \\
%       |pentagram|& \VertexSamples{pentagram} \\
%       |hexagram| & \VertexSamples{hexagram}
%     \end{tabular}
%   \end{center}
%   \caption{Available vertex shapes and fill styles.}
%   \label{tab:vertex-shapes}
% \end{table}
%
% \DescribeMacro{\fmfblob}
% Draw a blob of the specified diameter at the vertices.
% |\fmfblob{|\meta{diameter}|}{|\meta{v1}\allowbreak
%   $[$|,|\ldots$]$|}| is equivalent to
% |\fmfv{decor.shape=circle,|\allowbreak|decor.filled=.5,|\allowbreak
%   |decor.size=|\meta{diameter}\allowbreak
%   |}{|\meta{v1}\allowbreak$[$|,|\ldots$]$|}|
%
% \DescribeMacro{\fmfdot}
% Draw a dot at the vertices given as arguments.
% |\fmfdot{|\meta{v1}\allowbreak
%   $[$|,|\ldots$]$|}| is equivalent to
% |\fmfv{decor.shape=circle,|\allowbreak|decor.filled=1,|\allowbreak
%   |decor.size=2thick|\allowbreak
%   |}{|\meta{v1}\allowbreak$[$|,|\ldots$]$|}|
%
% \DescribeMacro{\fmfposition}
% Calculate the positions of the vertices based on the arcs which are
% defined up to this point.  Usually this calculation is performed
% automatically at the end of the |fmfchar| environment. Calling it
% explicitely, is useful for adding arcs which should not enter the
% calculation.
%
% \DescribeMacro{\fmfforce}
% |\fmfforce{|\meta{pos}|}{|\meta{v1}\allowbreak$[$|,|\ldots$]$|}|
% forces the position \meta{pos} of the vertices \meta{v1}\ldots,
% bypassing the automatic layout. 
%
% \DescribeMacro{\fmfshift}
% |\fmfforce{|\meta{dist}|}{|\meta{v1}\allowbreak$[$|,|\ldots$]$|}|
% shifts the position of the vertices \meta{v1}\ldots{} by \meta{dist}
% from the automatic layout.
%
% \DescribeMacro{\fmffixed}
% |\fmfforce{|\meta{dist}|}{|\meta{v1}\allowbreak$[$|,|\ldots$]$|}|
% fixes the distance between subsequent vertices in the list
% \meta{v1}\ldots{} to \meta{dist}.
% This command should be used with care, because it is possible to
% overconstrain the layout of the graph and the error messages will be
% obscure to a novice user.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Examples}
%
% As an example, consider drawing a straightforward box diagram,
% familier from $K$-$\bar K$, $D$-$\bar D$, and  $B$-$\bar B$ mixing.
% The commands for the labels are not shown here, they are discussed
% in section~\ref{sec:labels}
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   We start the diagram and pick up a thick pen:
%   \begin{verbatim}
%   \begin{fmfchar}(40,25)
%     \fmfpen{thick}
%   \end{verbatim}
%   The incoming and outcoming vertices are placed on the left and
%   right hand side, respectively:
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2}
%   \end{verbatim}
%   Now we tell \FMF{} how the arcs are connected.
%   \begin{verbatim}
%     \fmf{fermion}{i1,v1,v3,o1}
%     \fmf{fermion}{o2,v4,v2,i2}
%     \fmf{photon}{v1,v2}
%     \fmf{photon}{v3,v4}
%   \end{verbatim}
%   Finally we tell \FMF{} to draw dots at the vertices and we're
%   done.
%   \begin{verbatim}
%     \fmfdot{v1,v2,v3,v4}
%   \end{fmfchar}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar*}(40,25)
%       \fmfpen{thick}
%       \fmfleft{i1,i2}
%       \fmflabel{$\noexpand\bar b$}{i1}
%       \fmflabel{$d$}{i2}
%       \fmfright{o1,o2}
%       \fmflabel{$\noexpand\bar d$}{o1}
%       \fmflabel{$b$}{o2}
%       \fmf{fermion}{i1,v1}
%       \fmf{fermion,label=$\noexpand\bar t,,\noexpand\bar c,,
%                           \noexpand\bar u$,l.side=right}{v1,v3}
%       \fmf{fermion}{v3,o1}
%       \fmf{fermion}{o2,v4}
%       \fmf{fermion,label=$t,,c,,u$,l.side=right}{v4,v2}
%       \fmf{fermion}{v2,i2}
%       \fmf{photon,label=$W^+$,l.side=left}{v1,v2}
%       \fmf{photon,label=$W^-$,l.side=right}{v3,v4}
%       \fmfdot{v1,v2,v3,v4}
%     \end{fmfchar*}
%   \end{center}
% \end{minipage}
% \label{page:simple-examples}
%
% Here is the resonant $s$-channel contribution to $e^+e^-\to 4f$.
% (From now on, we do no longer display the
% |\begin{fmfchar}(40,25)|, |\fmfpen{thick}|, \ldots,
% |\end{fmfchar}| surrounding all pictures.)
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2,o3,o4}
%       \fmf{fermion}{i1,v1,i2}
%     \fmf{photon}{v1,v2}
%     \fmfblob{.15w}{v2}
%       \fmf{photon}{v2,v3}
%         \fmf{fermion}{o1,v3,o2}
%       \fmf{photon}{v2,v4}
%         \fmf{fermion}{o4,v4,o3}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.38\linewidth}
%   \begin{center}
%     \fmfframe(0,5)(5,7){%
%       \begin{fmfchar*}(40,25)
%         \fmfpen{thick}
%         \fmfleft{i1,i2}
%         \fmfright{o1,o2,o3,o4}
%           \fmflabel{$e_-$}{i1}
%           \fmflabel{$e_+$}{i2}
%           \fmf{fermion}{i1,v1,i2}
%         \fmf{photon}{v1,v2}
%         \fmfblob{.15w}{v2}
%           \fmf{photon}{v2,v3}
%             \fmflabel{$\noexpand\mu_+$}{o1}
%             \fmflabel{$\noexpand\nu_{\noexpand\mu}$}{o2}
%             \fmf{fermion}{o1,v3,o2}
%           \fmf{photon}{v2,v4}
%             \fmflabel{$\noexpand\bar c$}{o4}
%             \fmflabel{$s$}{o3}
%             \fmf{fermion}{o4,v4,o3}
%       \end{fmfchar*}}
%   \end{center}
% \end{minipage}
%
% And the resonant $t$-channel contribution:
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2,o3,o4}
%     \fmf{fermion}{i1,v1,v2,i2}
%       \fmf{photon}{v1,v3}
%         \fmf{fermion}{o1,v3,o2}
%       \fmf{photon}{v2,v4}
%         \fmf{fermion}{o4,v4,o3}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.38\linewidth}
%   \begin{center}
%     \fmfframe(0,5)(5,7){%
%       \begin{fmfchar*}(40,25)
%         \fmfpen{thick}
%         \fmfleft{i1,i2}
%         \fmfright{o1,o2,o3,o4}
%         \fmflabel{$e_-$}{i1}
%         \fmflabel{$e_+$}{i2}
%         \fmf{fermion}{i1,v1,v2,i2}
%           \fmf{photon}{v1,v3}
%             \fmflabel{$\noexpand\mu_+$}{o1}
%             \fmflabel{$\noexpand\nu_{\noexpand\mu}$}{o2}
%             \fmf{fermion}{o1,v3,o2}
%           \fmf{photon}{v2,v4}
%             \fmflabel{$\noexpand\bar c$}{o4}
%             \fmflabel{$s$}{o3}
%             \fmf{fermion}{o4,v4,o3}
%       \end{fmfchar*}}
%   \end{center}
% \end{minipage}
%
% Actually, these three diagrams can be improved slightly by using
% |phantom| arcs, which will be discussed in the next section.
%
% Two point loop diagrams pose another set of problems.  We
% must have a way of specifying that one or more of the lines
% connecting the two vertices are \emph{not} connected by a straight
% line.  The options |left|, |right| and |straight| offer the
% possibility to connect two vertices by a semicircle detour, either
% on the left or on the right.  Since by default all lines contribute
% to the tension between two vertices, the |tension| option allows us
% to reduce this tension.  The next examples shows both options in
% action.  The lower fermion line is given an tension of~$1/3$ to
% make is symmetrical with the upper line with consists of three parts.
% The loop photon is using a detour on the right and does not
% contribute any tension.
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1}
%     \fmf{fermion,tension=1/3}{i1,v1}
%     \fmf{plain}{v1,v2}
%     \fmf{fermion}{v2,v3}
%     \fmf{photon,right,tension=0}{v2,v3}
%     \fmf{plain}{v3,i2}
%     \fmf{photon}{v1,o1}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar*}(40,25)
%       \fmfpen{thick}
%       \fmfleft{i1,i2}
%       \fmflabel{$p^{\noexpand\prime}$}{i1}
%       \fmflabel{$p$}{i2}
%       \fmfright{o1}
%       \fmflabel{$p+p^{\noexpand\prime}$}{o1}
%       \fmf{fermion,tension=1/3}{i1,v1}
%       \fmf{plain}{v1,v2}
%       \fmf{fermion,label=$p-k$,l.side=left}{v2,v3}
%       \fmf{photon,right,tension=0,label=$k$}{v2,v3}
%       \fmf{plain}{v3,i2}
%       \fmf{photon}{v1,o1}
%     \end{fmfchar*}
%   \end{center}
% \end{minipage}
%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Labels}
% \label{sec:labels}
%
% Let us now come back to the examples on
% page~\pageref{page:simple-examples} and discuss how to add the
% labels.
%
% \DescribeMacro{\fmflabel}
% The macro |\fmflabel{|\meta{label}|}{|\meta{v}|}| adds the label
% \meta{label} to the vertex \meta{v}.  In the current implementation,
% there can be only a single label for each vertex.  Thus earlier
% calls to |\fmflabel| for the same vertex will be overwritten.
% \meta{label} will be placed with the |\put| command of the \LaTeX{}
% |picture| environment.  \emph{It is absolutely necessary to quote
% \emph{each} \TeX{} control sequence appearing in \meta{label} with}
% |\noexpand|.  \emph{Otherwise all kinds of disasters are bound to
% happen, causing at the very least some obscure error messages!}
% Note that the |fmfchar*| environment must be used to use labels,
% they will silently disappear in |fmfchar|.
%
% |\fmflabel| gives the user \emph{no} control on the placement of
% the the label (see below for a more fine-grained control provided by
% the options to the |\fmfv| macro).  The label is placed using the
% following algorithm:
% \begin{enumerate}
%   \item{} The reference point of the box containing \meta{label} is
%     placed at the distance |3thick| on the continuation of the
%     straight line connecting the center of the picture with the
%     vertex \meta{v}.
%   \item{} The reference point of the box is chosen such that the
%     contents of the box is on the outside of the vertex (with
%     respect to the center of the diagram).  It is chosen from the
%     four corners and the four midpoints of the sides.
% \end{enumerate}
%
% Therefore the four external particles in the~$B$-$\bar B$ mixing
% diagram on page~\pageref{page:simple-examples} are labelled simply
% by:
% \begin{verbatim}
%   \fmflabel{$\noexpand\bar b$}{i1}
%   \fmflabel{$d$}{i2}
%   \fmflabel{$\noexpand\bar d$}{o1}
%   \fmflabel{$b$}{o2}
% \end{verbatim}
%
% \begin{dubious}
%   Explain more of the |label| option and the default placement rules.
% \end{dubious}
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Advanced usage}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Shrinking}
%
% \DescribeEnv{fmfshrink}
% Shrink the lineswidths and similar parameters in the enclosed section.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Multiple vertices and arcs}
%
% \DescribeMacro{\fmfleftn}
% \DescribeMacro{\fmfrightn}
% \DescribeMacro{\fmfbottomn}
% \DescribeMacro{\fmftopn}
% \DescribeMacro{\fmfsurroundn}
% The macro is|\fmfleftn| is similar to |\fmfleft|, but
% |\fmfleftn{|\meta{v}\allowbreak|}{|\meta{n}|}| places the
% vertices
% \meta{v$[$1$]$}\ldots\meta{v$[$n$]$}.  Analogously for
% the macros |\fmfrightn|, |\fmfbottomn|, |\fmftopn| and
% |\fmfsurroundn|.
%
% \DescribeMacro{\fmfvn}
% The macro |\fmfvn| is similar to |\fmfv|, but
% |\fmfvn{|\meta{vertex}\allowbreak|}{|\meta{v}\allowbreak|}{|\meta{n}|}|
% places the vertices \meta{v$[$1$]$}\ldots\meta{v$[$n$]$}.
%
% \DescribeMacro{\fmfdotn}
% \DescribeMacro{\fmfblobn}
% The macros |\fmfdotn| and |\fmfblobn| are similar to the |\fmfdot|
% and |\fmfblob|, but |\fmfdotn{|\meta{v}|}{|\meta{n}|}| places the
% vertices \meta{v$[$1$]$}\ldots\meta{v$[$n$]$}.  Analogously for
% |\fmfblobn|.
%
% \DescribeEnv{fmffor}
% The environment |\begin{fmffor}{|\meta{var}\allowbreak
%   |}{|\meta{from}\allowbreak|}{|\meta{step}\allowbreak
%   |}{|\meta{to}\allowbreak|}|\allowbreak\meta{body}\allowbreak
%   |\end{fmffor}|
% executes \meta{body} multiple times, setting \meta{var} to
% $\meta{from}, \meta{from}+\meta{step}, \ldots, \meta{to}$.
%
% \DescribeMacro{\fmfcyclen}
% \DescribeMacro{\fmfrcyclen}
% The macro |\fmfcyclen{|\meta{style}|}{|\meta{v}|}{|\meta{n}|}|
% cyclically connects the vertices
% \meta{v$[$1$]$}\ldots\meta{v$[$n$]$}. |\fmfcyclen| operates in
% reverse order.
%
% An advanced application of the above \FMF{} features is shown in
% figure~\ref{fig:euler-heisenberg}, which is generated by calling
% the \TeX{} macro
% \begin{verbatim}
%   \def\EulerHeisenberg#1{%
%      \begin{fmfchar}(40,25)
%        \fmfpen{thick}
%        \fmfsurroundn{e}{#1}
%        \begin{fmffor}{n}{1}{1}{#1}
%          \fmf{photon}{e[n],i[n]}
%        \end{fmffor}
%        \fmfcyclen{fermion,tension=#1/8}{i}{#1}
%      \end{fmfchar}}
% \end{verbatim}
% with the arguments 4, 6, 8, and 10, respectively.
% \def\EulerHeisenberg#1{%
%    \begin{fmfchar}(40,25)
%      \fmfpen{thick}
%      \fmfsurroundn{e}{#1}
%      \begin{fmffor}{n}{1}{1}{#1}
%        \fmf{photon}{e[n],i[n]}
%      \end{fmffor}
%      \fmfcyclen{fermion,tension=#1/8}{i}{#1}
%    \end{fmfchar}}
% \begin{figure}
%   \begin{center}
%     \EulerHeisenberg{4} \qquad \EulerHeisenberg{6}
%   \end{center}
%   \begin{center}
%       \EulerHeisenberg{8} \qquad \EulerHeisenberg{10}
%   \end{center}
%   \caption{Higher order terms in the Euler-Heisenberg lagrangian.}
%   \label{fig:euler-heisenberg}
% \end{figure}
%
% Similarly, we can draw the diagrams in figures~\ref{fig:PP-rings}
% and~\ref{fig:PP-rings} from many particle physics:
% \begin{verbatim}
%   \def\PPRing#1{%
%     \begin{fmfchar}(20,20)
%       \fmfsurroundn{v}{#1}
%       \fmfdotn{v}{#1}
%       \fmfcyclen{fermion,right=0.25}{v}{#1}
%       \fmfcyclen{fermion,left=0.25}{v}{#1}
%     \end{fmfchar}}
%   \def\PHRing#1{%
%     \begin{fmfchar}(20,20)
%       \fmfsurroundn{v}{#1}
%       \fmfdotn{v}{#1}
%       \fmfcyclen{fermion,right=0.25}{v}{#1}
%       \fmfrcyclen{fermion,right=0.25}{v}{#1}
%     \end{fmfchar}}
% \end{verbatim}
% \def\PPRing#1{%
%   \begin{fmfchar}(20,20)
%     \fmfsurroundn{v}{#1}
%     \fmfdotn{v}{#1}
%     \fmfcyclen{fermion,right=0.25}{v}{#1}
%     \fmfcyclen{fermion,left=0.25}{v}{#1}
%   \end{fmfchar}}
% \def\PHRing#1{%
%   \begin{fmfchar}(20,20)
%     \fmfsurroundn{v}{#1}
%     \fmfdotn{v}{#1}
%     \fmfcyclen{fermion,right=0.25}{v}{#1}
%     \fmfrcyclen{fermion,right=0.25}{v}{#1}
%   \end{fmfchar}}
% \begin{figure}
%   \begin{center}
%     \PPRing{3}\qquad\PPRing{4}\qquad\PPRing{5}\qquad\PPRing{6}
%   \end{center}
%   \caption{Particle-particle ring diagrams}
%   \label{fig:PP-rings}
% \end{figure}
% \begin{figure}
%   \begin{center}
%     \PHRing{3}\qquad\PHRing{4}\qquad\PHRing{5}\qquad\PHRing{6}
%   \end{center}
%   \caption{Particle-hole ring diagrams}
%   \label{fig:PH-rings}
% \end{figure}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Tight arcs}
%
% If you add to any arc one or more |phantom| arcs they will cause
% a tighter bonding between the vertices involved
% \begin{verbatim}
%   \fmf{fermion}{v1,v2}
%   \fmf{phantom}{v1,v2}
% \end{verbatim}
% which is equivalent to
% \begin{verbatim}
%   \fmf{fermion,tension=2}{v1,v2}
% \end{verbatim}
% The |phantom| arc has to be added \emph{before} any |\fmfposition|
% involving these vertices, of course.  Here is an example from deep
% inelastic scattering.  (We do not show the |\fmfcmd{}|s in this
% example which are used for decorating the incoming proton and do not
% affect \FMF's layout decisions.)
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{ip,il}
%     \fmfright{oq1,oq2,d1,oq3,d2,d3,ol}
%     \fmf{fermion}{ip,vp,vq,oq3}
%     \fmf{fermion}{vp,oq1}
%     \fmf{fermion}{vp,oq2}
%     \fmf{photon}{vl,vq}
%     \fmf{fermion}{il,vl,ol}
%     \fmfblob{.15w}{vp}
%     \fmfdot{vq}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar}(40,25)
%       \fmfpen{thick}
%       \fmfleft{ip,il}
%       \fmfright{oq1,oq2,d1,oq3,d2,d3,ol}
%       \fmf{fermion}{ip,vp,vq,oq3}
%       \fmf{fermion}{vp,oq1}
%       \fmf{fermion}{vp,oq2}
%       \fmf{photon}{vl,vq}
%       \fmf{fermion}{il,vl,ol}
%       \fmfposition
%       \fmfforce{vloc ip+(0,2thick)}{ipp}
%       \fmfforce{vloc ip-(0,2thick)}{ipm}
%       \fmfforce{vloc vp+(0,2thick)}{vpp}
%       \fmfforce{vloc vp-(0,2thick)}{vpm}
%       \fmfshift{0.12 (vloc ip - vloc vp)}{vpp}
%       \fmfshift{0.10 (vloc ip - vloc vp)}{vpm}
%       \fmf{plain}{ipp,vpp}
%       \fmf{plain}{ipm,vpm}
%       \fmfblob{.15w}{vp}
%       \fmfdot{vq}
%     \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% As it stands, all vertices come out too far to the right, because
% the greater number of outgoing lines pulls them over.  Adding
% |\fmf{phantom}| makes the bond between the incoming vertices and the
% interactions tighter and produces a better balanced picture:
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{ip,il}
%     \fmfright{oq1,oq2,d1,oq3,d2,d3,ol}
%     \fmf{fermion}{ip,vp,vq,oq3}
%     \fmf{phantom}{ip,vp}
%     \fmf{fermion}{vp,oq1}
%     \fmf{fermion}{vp,oq2}
%     \fmf{photon}{vl,vq}
%     \fmf{fermion}{il,vl,ol}
%     \fmf{phantom}{il,vl}
%     \fmfblob{.15w}{vp}
%     \fmfdot{vq}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar}(40,25)
%       \fmfpen{thick}
%       \fmfleft{ip,il}
%       \fmfright{oq1,oq2,d1,oq3,d2,d3,ol}
%       \fmf{fermion}{ip,vp,vq,oq3}
%       \fmf{phantom}{ip,vp}
%       \fmf{fermion}{vp,oq1}
%       \fmf{fermion}{vp,oq2}
%       \fmf{photon}{vl,vq}
%       \fmf{fermion}{il,vl,ol}
%       \fmf{phantom}{il,vl}
%       \fmfposition
%       \fmfforce{vloc ip+(0,2thick)}{ipp}
%       \fmfforce{vloc ip-(0,2thick)}{ipm}
%       \fmfforce{vloc vp+(0,2thick)}{vpp}
%       \fmfforce{vloc vp-(0,2thick)}{vpm}
%       \fmfshift{0.16 (vloc ip - vloc vp)}{vpp}
%       \fmfshift{0.14 (vloc ip - vloc vp)}{vpm}
%       \fmf{plain}{ipp,vpp}
%       \fmf{plain}{ipm,vpm}
%       \fmfblob{.15w}{vp}
%       \fmfdot{vq}
%     \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Loose arcs}
%
% Adding arcs \emph{after} any |\fmfposition| involving these
% vertices will make these arcs loose, i.e.~they will not contribute
% to the bonding between the vertices.
%
% Consider the following example: suppose we want to draw a ladder
% diagram contributing to the quark form factor.  Simply linking in
% the gluons does not produce a satisfactory result:
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1} \fmfright{o1,o2}
%     \fmf{photon}{i1,v4}
%     \fmf{quark}{o1,v1,v2,v3,v4,v5,v6,v7,o2}
%     \fmf{gluon}{v1,v7}
%     \fmf{gluon}{v2,v6}
%     \fmf{gluon}{v3,v5}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%    \begin{fmfchar}(40,25)
%      \fmfpen{thick}
%      \fmfleft{i1} \fmfright{o1,o2}
%      \fmf{photon}{v4,i1}
%      \fmf{quark}{o1,v1,v2,v3,v4,v5,v6,v7,o2}
%      \fmf{gluon}{v1,v7}
%      \fmf{gluon}{v2,v6}
%      \fmf{gluon}{v3,v5}
%    \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% What went wrong?  Obviously the gluons are bonding the quark lines
% too strongly.  The fix is simple: just exclude the gluons from the
% calculation and add them later as infinitely stretchable:
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1} \fmfright{o1,o2}
%     \fmf{photon}{i1,v4}
%     \fmf{quark}{o1,v1,v2,v3,v4,v5,v6,v7,o2}
%     \fmfposition
%     \fmf{gluon}{v1,v7}
%     \fmf{gluon}{v2,v6}
%     \fmf{gluon}{v3,v5}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%    \begin{fmfchar}(40,25)
%      \fmfpen{thick}
%      \fmfleft{i1} \fmfright{o1,o2}
%      \fmf{photon}{v4,i1}
%      \fmf{quark}{o1,v1,v2,v3,v4,v5,v6,v7,o2}
%      \fmfposition
%      \fmf{gluon}{v1,v7}
%      \fmf{gluon}{v2,v6}
%      \fmf{gluon}{v3,v5}
%    \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% Another instructive example is the following: imagine you want to
% draw a typical non-resonant contribution to~$e^+e^-\to 4f$.  The
% obvious solution doesn's look right.
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2,o3,o4}
%     \fmf{fermion}{i1,v1,i2}
%     \fmf{photon}{v1,v2}
%     \fmf{fermion}{o1,v2,v3,o4}
%     \fmf{photon}{v3,v4}
%     \fmf{fermion}{o3,v4,o2}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar}(40,25)
%       \fmfpen{thick}
%       \fmfleft{i1,i2}
%       \fmfright{o1,o2,o3,o4}
%       \fmf{fermion}{i1,v1,i2}
%       \fmf{photon}{v1,v2}
%       \fmf{fermion}{o1,v2,v3,o4}
%       \fmf{photon}{v3,v4}
%       \fmf{fermion}{o3,v4,o2}
%     \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% One way to fix it is to |\fmfshift| the three rightmost vertices by
% hand:
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2,o3,o4}
%     \fmf{fermion}{i1,v1,i2}
%     \fmf{photon}{v1,v2}
%     \fmf{fermion}{o1,v2,v3,o4}
%     \fmf{photon}{v3,v4}
%     \fmf{fermion}{o3,v4,o2}
%     \fmfposition
%     \fmfshift{-.1w,0}{v2,v3,v4}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar}(40,25)
%       \fmfpen{thick}
%       \fmfleft{i1,i2}
%       \fmfright{o1,o2,o3,o4}
%       \fmf{fermion}{i1,v1,i2}
%       \fmf{photon}{v1,v2}
%       \fmf{fermion}{o1,v2,v3,o4}
%       \fmf{photon}{v3,v4}
%       \fmf{fermion}{o3,v4,o2}
%       \fmfposition
%       \fmfshift{-.1w,0}{v2,v3,v4}
%     \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% A smarter solution is again to make certain arcs stretchable:
% \vspace*{\baselineskip}
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%     \fmfleft{i1,i2}
%     \fmfright{o1,o2,o3,o4}
%     \fmf{fermion}{i1,v1,i2}
%     \fmf{photon}{v1,v2}
%     \fmf{fermion}{o1,v2,v3,o4}
%     \fmfposition
%     \fmf{photon}{v3,v4}
%     \fmf{fermion}{o3,v4,o2}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar}(40,25)
%       \fmfpen{thick}
%       \fmfleft{i1,i2}
%       \fmfright{o1,o2,o3,o4}
%       \fmf{fermion}{i1,v1,i2}
%       \fmf{photon}{v1,v2}
%       \fmf{fermion}{o1,v2,v3,o4}
%       \fmfposition
%       \fmf{photon}{v3,v4}
%       \fmf{fermion}{o3,v4,o2}
%     \end{fmfchar}
%   \end{center}
% \end{minipage}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Avoiding continuously tight and loose arcs}
%
% I have been very reluctant to implement continuously tight and loose
% arcs in \FMF, because it introduces to much opportunity for
% ``fiddling'' on the user's part.  However, since the present
% implementation blends rather nicely with the options syntax, I have
% decided to add it anyway.  I hope that most diagrams will be created
% without too much ``fiddling''.
% 
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Raw \MF}
%
% Some more advanced features of \FMF{} are more conveniently
% accessed through raw \MF{} commands.  This can either be
% achieved by preparing a \MF{} input file or by using |\fmfcmd|
% extensively.  The latter apprach is usally more convenient.
%
% \DescribeMacro{\fmfcmd}
% The |\fmfcmd| macro writes its argument into the \MF{} input
% file generated by \FMF.  While some experience in using
% \MF{} doesn't hurt here, this approach can simplify the
% production of complex diagrams considerably.  
%
% Here's an interesting ``abuse'' of \FMF.  Using the undocumented
% \MF{} macros (like |vdraw_vertex_label|) is possible, though not
% supported.  In a future versions, these features will be made
% available through supported interfaces.
%
% \begin{minipage}{0.6\linewidth}
%   \begin{verbatim}
%   \begin{fmfchar*}(40,40)\fmfcmd{
%     pair o,xm,xp,ym,yp;
%     pair v.loc; string v.lbl;
%     o:=(.5w,.1h);
%     xm:=(0,.1h); xp:=(w,.1h);
%     ym:=(.5w,0); yp:=(.5w,h);
%     v.loc := xp; v.lbl := "$x$";
%     v.lbl.ang := -135; v.lbl.dist := 2;
%     vdraw_vertex_label v;
%     v.loc := yp; v.lbl := "$y=x^2$";
%     vdraw_vertex_label v;
%     pickup pencircle scaled thin;
%     draw xm--xp; draw ym--yp;
%     pickup pencircle scaled thick;
%     xs:=xpart(xp-o); ys:=ypart(yp-o);
%     draw (o + (-xs,ys)) for n = -9 upto 10:
%       --(o + (xs*(n/10),ys*((n/10)**2)))
%     endfor;}
%   \end{fmfchar*}
%   \end{verbatim}
% \end{minipage}
% \hfill
% \begin{minipage}{0.35\linewidth}
%   \begin{center}
%     \begin{fmfchar*}(40,40)\fmfcmd{
%       pair o,xm,xp,ym,yp;
%       pair v.loc; string v.lbl;
%       o:=(.5w,.1h);
%       xm:=(0,.1h); xp:=(w,.1h);
%       ym:=(.5w,0); yp:=(.5w,h);
%       v.loc := xp; v.lbl := "$x$";
%       v.lbl.ang := -135; v.lbl.dist := 2;
%       vdraw_vertex_label v;
%       v.loc := yp; v.lbl := "$y=x^2$";
%       vdraw_vertex_label v;
%       pickup pencircle scaled thin;
%       draw xm--xp; draw ym--yp;
%       pickup pencircle scaled thick;
%       xs:=xpart(xp-o); ys:=ypart(yp-o);
%       draw (o + (-xs,ys)) for n = -9 upto 10:
%         --(o + (xs*(n/10),ys*((n/10)**2)))
%       endfor;}
%     \end{fmfchar*}
%   \end{center}
% \end{minipage}
% 
% Finally, for the curious, here is how to draw the circular gluons in
% figure~\ref{fig:gluons}:
% \begin{verbatim}
%   \fmfcmd{draw_gluon (fullcircle scaled .5w shifted (.5w,.5h));}
%   \fmfcmd{draw_gluon (reverse fullcircle scaled .5w shifted (.5w,.5h));}
% \end{verbatim}
%
% \begin{figure}
%   \begin{center}
%     \begin{fmfchar}(40,40)
%       \fmfcmd{draw_gluon (fullcircle scaled .5w shifted (.5w,.5h));}
%     \end{fmfchar}
%     \qquad
%     \begin{fmfchar}(40,40)
%       \fmfcmd{draw_gluon (reverse fullcircle scaled .5w shifted (.5w,.5h));}
%     \end{fmfchar}
%   \end{center}
%   \caption{Circular gluons.}
%   \label{fig:gluons}
% \end{figure}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Limitations}
%
% Currently the most severe limitation lies in the size of the
% generated pictures.  The largest number \MF{} can represent
% internally is~4095.99998 and this is also the largest value any
% coordinate measured in pixels can assume.  At the most popular
% laserprinter resolution of~300 dots per inch (dpi), this corresponds
% to a horizontal and vertical extension of about~346mm, which is
% plenty and we're more likely to hit the internal limits on the
% complexity of a picture.  However, at the proof mode resolution
% of~2601.72dpi, this is reduced to slightly less than~40mm and we're
% running the risk of arithmetic overflow in internal calculations much
% earlier.
%
% There are two potential solutions of different scope and complexity:
% \begin{itemize}
%   \item{} Since John Hobby's \MP{} is now available without a
%     non-disclosure agreement from AT\&T, one solution is to replace
%     \MF{} by \MP, which doesn't suffer from the size
%     limitations\footnote{%
%       Right now, \FMF's \MP{} support is still
%       somewhat kludged, but the functionality is there.}
%     This comes with a small price paid in reduced portability of the
%     generated output, but as already stated above in the case of
%     |axodraw|, the ubiquity of PostScript printers (and the free
%     GhostScript interpreter) makes this a minor point.
%   \item{} The more ambitious solutions will be ``virtual pictures''
%     (see section~\ref{sec:virtual-pictures}).
% \end{itemize}
%
% \end{fmffile}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section*{Acknowledgements}
%
% I am most grateful to Wolfgang Kilian, who pushed \FMF's predecessor
% |feynman.mf| to its limits~\cite{Kil94}.  His needs were valuable
% input to \FMF.  Thanks also to Angelika Himmler and Uwe Mayer for
% acting as guinea pigs.
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \begin{thebibliography}{99}
%   \bibitem{TeX} Donald E.~Knuth, \textit{The \TeX{}book},
%      Addison-Wesley, Reading, 1986.
%   \bibitem{LaTeX} Leslie Lambort, \textit{\LaTeX{} --- A
%     Documentation Preparation System},
%     Addison-Wesley, Reading, 1985.
%   \bibitem{LaTeX-Companion} Michel Goosens, Frank Mittelbach, and
%     Alexander Samarin, \textit{The \LaTeX{} Companion},
%     Addison-Wesley, Reading, 1994.
%   \bibitem{MF} Donald E.~Knuth, \textit{The \MF{}book},
%      Addison-Wesley, Reading, 1986.
%   \bibitem{MetaPost} John D.~Hobby, \textit{A User's Manual for
%     \MP}, Computer Science Report \#162, AT\&T Bell
%     Laboratories, April 1992.
%   \bibitem{hoenig} Alan Hoenig, \textit{When \TeX{} and \MF{}
%     Work Together}, in \textit{Proceedings of the 7th European
%     \TeX{} Conference, Prague}, p.~1, September 1992.
%   \bibitem{levine} Micheal J.~S.~Levine,
%     Comp.~Phys.~Comm.~\textbf{58} (1990) 181.
%   \bibitem{axodraw} Jos Vermaseren, \texttt{axodraw}.
%   \bibitem{mfpic} Thomas E.~Leathrum, \texttt{mfpic}.
%   \bibitem{madgraph} Tim Stelzer and Bill Long, \texttt{MADGRAPH},
%     hep-ph/93mmxxx.
%   \bibitem{Kil94} Wolfgang Kilian, Doctoral Thesis, Technical
%     University Darmstadt, 1994.
% \end{thebibliography}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \StopEventually{\PrintIndex\PrintChanges}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section{\TeX{} macros}
%
% It's is good practice to identify this version of the document style
% option.  We do this by parsing an RCS |Id| string and storing the
% result in the conventional \TeX{} control sequences:
% \changes{1.1}{1994/05/19}{%
%   Don't loose on {\tt RCS} strings even iff the dollar signs have
%   been removed.}
% \changes{1.9}{1995/02/18}{\LaTeX~2.09 compatibility}
%    \begin{macrocode}
%<*style>
%<!209>\NeedsTeXFormat{LaTeX2e}
{\def\RCS#1#2\endRCS{%
  \ifx$#1%
    \@RCS $#2 \endRCS
  \else
    \@RCS $*: #1#2$ \endRCS
  \fi}%
 \def\@RCS $#1: #2,v #3 #4 #5 #6$ \endRCS{%
   \gdef\filename{#2}%
   \gdef\fileversion{v#3}%
   \gdef\filedate{#4}%
   \gdef\docdate{#4}}%
\RCS feynmf.dtx,v 1.10 1995/02/18 16:42:18 ohl Exp \endRCS}%
%    \end{macrocode}
%
% And now the standard procedure:
% \changes{1.4}{1994/05/27}{%
%   \MP{} support: identification part, include
%   \texttt{graphicx} and pass options.}
%    \begin{macrocode}
%<*!mp>
%<!209>\ProvidesPackage{feynmf}[\filedate\space LaTeX2e package]
\typeout{Package: `feynmf'
   \fileversion\space <\filedate> (tho) PRELIMINARY TEST RELEASE}
\wlog{English documentation \@spaces<\docdate> (tho)}
%</!mp>
%<*mp>
%<!209>\ProvidesPackage{feynmp}[\filedate\space LaTeX2e package]
\typeout{Package: `feynmp'
   \fileversion\space <\filedate> (tho) PRELIMINARY TEST RELEASE}
\wlog{English documentation \@spaces<\docdate> (tho)}
%    \end{macrocode}
% Every option we don't understand (that is \emph{every} option) is
% sent down to |graphicx|:
%    \begin{macrocode}
%<*!209>
\DeclareOption*{\PassOptionsToPackage{\CurrentOption}{graphicx}}
\ProcessOptions
%    \end{macrocode}
% For the sake of Portabilitical Correctness, we use \LaTeX's
% |graphicx| for including PostScript, instead of the simpler |epsf|
% which comes with |dvips| and would have sufficed
%    \begin{macrocode}
\RequirePackage{graphicx}
%</!209>
%<209>\input epsf.sty
%</mp>
%    \end{macrocode}
% Compatibility macros for \LaTeX~2.09:
%    \begin{macrocode}
%<*209>
\def\InputIfFileExists#1#2#3{%
  \openin\@inputcheck#1 %
  \ifeof\@inputcheck
    \closein\@inputcheck
    #3%
  \else
    \closein\@inputcheck
    #2%
    \input{#1}
  \fi}
\def\IfFileExists#1#2#3{%
  \openin\@inputcheck#1 %
  \ifeof\@inputcheck
    \closein\@inputcheck
    #3%
  \else
    \closein\@inputcheck
    #2%
  \fi}
%</209>
%    \end{macrocode}
%
% \begin{dubious}
%   We should |\||mdqon| at the end only if the German extensions are
%   really active, not just loaded.
% \end{dubious}
%    \begin{macrocode}
\let\mdqrestore\relax
\@ifundefined{mdqoff}{}{%
  \mdqoff
  \let\mdqrestore\mdqon}
%    \end{macrocode}
%
% \begin{macro}{\fmfcmd}
% The entrance through which our commands enter the world of
% \MF.  Note the |\ignorespaces|: we need to avoid spurious
% blanks in the output list.
%    \begin{macrocode}
\newwrite\@outfmf
\def\fmfcmd#1{%
  \immediate\write\@outfmf{#1}\ignorespaces}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmffile}
% This environment encloses each \MF{} input file.  The single
% argument gives the name of the file.
% \changes{1.1}{1994/05/16}{%
%   Stupid: {\tt fileversion} can be reset by other packages, store
%   the current value in {\tt fmf@fileversion} and use this one.}
% \changes{1.1}{1994/05/20}{%
%   Pass RCS revision in a string.}
% \changes{1.4}{1994/05/27}{\MP{} support: write \MP{} file.}
% \changes{1.9}{1995/01/18}{%
%   Protect against wrong arguments to \texttt{fmffile}.}
%    \begin{macrocode}
{\catcode`\%=11\gdef\p@rcent{%}}
\edef\fmf@fileversion{\fileversion}
\def\fmffile#1{%
  \def\thefmffile{#1}%
  \equaltojobname{\thefmffile}{%
    \errhelp={The argument of \fmffile MUST NOT be identical to the^^J%
              name of your main input file!  I will use fmfdefault.mf^^J%
              this time around, but you'd better fix your code now!}%
    \errmessage{Invalid arument of \string\fmffile!}%
    \def\thefmffile{fmfdefault}}{}%
%<*!mp>
  \immediate\openout\@outfmf=\thefmffile.mf\relax
  \fmfcmd{\p@rcent\space \thefmffile.mf -- do not edit, %
          generated automatically by \jobname.tex^^J%
          input feynmf^^J%
          require_RCS_revision "\expandafter\@gobble\fmf@fileversion";}%
%</!mp>
%<*mp>
  \immediate\openout\@outfmf=\thefmffile.mp\relax
  \fmfcmd{\p@rcent\space \thefmffile.mp -- do not edit, %
          generated automatically by \jobname.tex^^J%
          input feynmp^^J%
          require_RCS_revision "\expandafter\@gobble\fmf@fileversion";}%
%</mp>
%    \end{macrocode}
% The following trick has been taken from |mfpic|~\cite{mfpic}:
% proceed even if the font is not available yet, because we have to
% write the \MF{} file first.
% \changes{1.4}{1994/05/27}{\MP{} support: don't open \texttt{tfm} file.}
%    \begin{macrocode}
%<*!mp>
  \batchmode
  \font\f@ynmf=\thefmffile
  \errorstopmode
%    \end{macrocode}
% Inform the user:
%    \begin{macrocode}
  \ifx\f@ynmf\nullfont
    \def\f@ynmf{feynmf character:}%
    \typeout{%
      feynmf: File \thefmffile.tfm not found:^^J%
      feynmf: Process \thefmffile.mf with METAFONT and then %
              reprocess this file.}%
  \else
    \typeout{%
      feynmf: File \thefmffile.tfm found.^^J%
      feynmf: Nevertheless, if the picture has changed, %
              reprocess \thefmffile.mf.^^J%
      feynmf: If dimension have changed, reprocess \thefmffile.mf %
              and \jobname.tex.}%
  \fi
%</!mp>
%    \end{macrocode}
% Count the characters
%    \begin{macrocode}
  \setcounter{fmfchar}{0}}
\let\thefmffile\relax
\newcounter{fmfchar}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\equaltojobname}
% Here's a kludge for comparing strings to |\jobname|.  I dont quite
% understand, why the |\meaning| hack is necessary, but |\jobname|
% behaves differently from other macros with respect to |\ifx|.
%    \begin{macrocode}
\def\equaltojobname#1#2#3{%
  \edef\@tempa{#1}%
  \edef\@tempa{\meaning\@tempa}%
  \edef\@tempb{\jobname}%
  \edef\@tempb{\meaning\@tempb}%
  \ifx\@tempa\@tempb
    #2
  \else
    #3
  \fi}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\endfmffile}
% And here is how we close the |fmffile| environment:
%    \begin{macrocode}
\def\endfmffile{%
  \fmfcmd{\p@rcent\space the end.^^J%
          end.^^J%
          endinput;}%
  \let\thefmffile\relax
  \immediate\closeout\@outfmf}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmf@char}
% This is the bulk of the environment used for each ``character''
% drawn by \MF.
% \changes{1.5}{1994/08/17}{%
%   Removed definiton of \texttt{sharp}.  It's never used and
%   conflicts with the $\sharp$ symbol.}
%    \begin{macrocode}
{\catcode`\#=11\gdef\sh@rp{#}}
\def\fmf@char#1#2{%
%    \end{macrocode}
% Make sure that a \MF{} file is open, otherwise \emph{really}
% obscure error messages are possible:
% \changes{1.3}{1994/05/23}{%
%   Make sure that a \MF{} file is open, otherwise \emph{really}
%   obscure error messages are possible.}
%    \begin{macrocode}
  \ifx\thefmffile\relax
    \errhelp={Outside a fmffile environment, I have no clue as to where^^J%
              the METAFONT commands should go.   I will use fmfdefault.mf^^J%
              for this character, but you'd better fix your code!}%      
    \errmessage{I detected a fmfchar environment outside of fmffile}%
    \fmffile{fmfdefault}
  \fi
%    \end{macrocode}
% We can't use |\stepcounter| because of the |amstext| option of
% AMS-\LaTeX{} disables it sometimes.
% \changes{1.9}{1995/01/07}{Don't use \texttt{stepcounter}.}
%    \begin{macrocode}
  \global\expandafter\advance\csname c@fmfchar\endcsname \@ne
%    \end{macrocode}
% Start \MF{} character:
%    \begin{macrocode}
  \fmfcmd{beginchar(\thefmfchar, #1*\the\unitlength\sh@rp, %
                                 #2*\the\unitlength\sh@rp, 0);^^J%
            "feynmf: \thefmfchar";}%
  \fmfcmd{LaTeX_unitlength:=\the\unitlength;}%
  \fmfinit
  \fmfpen{thin}}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmfchar}
% The plain version, no labels, no enclosing |picture| environment
%    \begin{macrocode}
\def\fmfchar(#1,#2){%
  \fmf@char{#1}{#2}%
%    \end{macrocode}
% Place the character:
% \changes{1.4}{1994/05/27}{\MP{} support: include PostScript file.}
% \changes{1.9}{1995/02/18}{\LaTeX~2.09 compatibility}
%    \begin{macrocode}
%<!mp>{\f@ynmf \char\value{fmfchar}}%
%<*mp>
  \leavevmode
  \IfFileExists{\thefmffile.\thefmfchar}%
%<*!209>
   {\includegraphics[type=eps,ext=\thefmfchar,read=\thefmfchar]%
      {\thefmffile}}%
%</!209>
%<*209>
   {\epsffile{\thefmffile.\thefmfchar}}%
%</209>
   {\typeout{%
      feynmp: File \thefmffile.\thefmfchar\space not found:^^J%
      feynmp: Process \thefmffile.mp with MetaPost and then %
              reprocess this file.}}%
%</mp>
  \ignorespaces}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\endfmfchar}
%    \begin{macrocode}
\def\endfmfchar{%
  \fmfposition
  \fmfdraw
  \fmfcmd{endchar;}}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmfchar*}
% The extended version, with labels and |picture| environment.
%    \begin{macrocode}
\@namedef{fmfchar*}(#1,#2){%
  \begin{picture}(#1,#2)
    \fmf@char{#1}{#2}%
%    \end{macrocode}
% Process the \MF{} output for labels (if any), enforcing |%| as
% comment character.
%    \begin{macrocode}
%<*!mp>
    {\catcode`\%=14\relax
      \grepfile{%
        \thefmffile.\thefmfchar}{%
        \thefmffile.log}{%
        \thefmffile.t\thefmfchar}}%
%</!mp>
%    \end{macrocode}
% Place the character:
% \changes{1.4}{1994/05/27}{\MP{} support: include PostScript file.}
%    \begin{macrocode}
%<!mp>\put(0,0){{\f@ynmf \char\value{fmfchar}}}%
%<*mp>
  \IfFileExists{\thefmffile.\thefmfchar}%
%<*!209>
   {\put(0,0){\includegraphics[type=eps,ext=\thefmfchar,read=\thefmfchar]%
                {\thefmffile}}}%
%</!209>
%<*209>
   {\put(0,0){\epsffile{\thefmffile.\thefmfchar}}}%
%</209>
   {\typeout{%
      feynmp: File \thefmffile.\thefmfchar\space not found:^^J%
      feynmp: Process \thefmffile.mp with MetaPost and then %
              reprocess this file.}}%
%</mp>
      \ignorespaces}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\endfmfchar*}
%    \begin{macrocode}
\@namedef{endfmfchar*}{%
    \endfmfchar
%    \end{macrocode}
% Enforce |%| as comment character:
%    \begin{macrocode}
    {\catcode`\%=14\relax
      \InputIfFileExists{\thefmffile.t\thefmfchar}{}{%
        \typeout{%
          feynmf: Label file \thefmffile.t\thefmfchar\space not found:^^J%
%<!mp>    feynmf: Process \thefmffile.mf with METAFONT and then %
%<mp>     feynmf: Process \thefmffile.mp with MetaPost and then %
                  reprocess this file.}}}%
  \end{picture}}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmfframe}
% This is used to allocate additional space around a |fmfchar*|, since
% the labels (or the diagram itself) might overshoot.
% |\fmfchar(|\meta{left}|,|\meta{top}|)(|\meta{right}|,|\meta{bottom}|){|%
% \meta{box}|}| puts an invisible frame of the given dimensions
% (measured in |\unitlength|) around \meta{box}.
%    \begin{macrocode}
\def\fmfframe(#1,#2)(#3,#4)#5{%
  \leavevmode
  \hbox{\vbox{\vskip#2\unitlength\par
              \hbox{\hskip#1\unitlength#5\hskip#3\unitlength}\par
              \vskip#4\unitlength}}}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmfpen}
% Picup a |pencircle| scaled by the argument.
%    \begin{macrocode}
\def\fmfpen#1{\fmfcmd{pickup pencircle scaled #1;}}
%    \end{macrocode}
% \end{macro}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Grep}
% \label{sec:grep}
%
% \begin{macro}{\grepfile}
% The macro |\grepfile{|\meta{pattern}|}{|\meta{in}|}{|\meta{out}|}|
% writes all lines matching |:|\meta{pattern}|:| from file \meta{in}
% to file \meta{out} after stripping off the pattern.
% \begin{dubious}
%   Pattern matching on lines with a single leading colon fails.
% \end{dubious}
% \changes{1.4}{1994/05/28}{%
%   Don't include the \texttt{grep} macros in the \MP{} version.
%   \texttt{write} makes them obsolete.}
%    \begin{macrocode}
%<*!mp>
\def\grepfile#1#2#3{%
  \begingroup
%    \end{macrocode}
% Hash the pattern and open the input and output streams:
%    \begin{macrocode}
    \edef\pattern{\csname*grep*#1*\endcsname}%
    \immediate\openin\grep@infile #2\relax
    \ifeof\grep@infile
    \else
      \grep@outopenfalse
%    \end{macrocode}
% Don't add anything at the end of input lines and don't expand
% anything we've read from the file:
%    \begin{macrocode}
      \endlinechar=-1
      \catcode`\\=12\relax
%    \end{macrocode}
% Loop over the input lines until end of file occurs:
%    \begin{macrocode}
      \loop
        \read\grep@infile to \grep@lbuf
        \ifeof\grep@infile
          \grep@contfalse
        \else
          \grep@conttrue
%    \end{macrocode}
% Iff the input line is not empty, use |\grep@aline| to examine its
% contents and, iff the pattern matched, write a line to the output file.
%    \begin{macrocode}
          \ifx\grep@lbuf\empty
          \else
            \expandafter\grep@aline\grep@lbuf\sentinel
            \ifx\pattern\grep@tag
%    \end{macrocode}
% Delayed open (this avoids empty files):
%    \begin{macrocode}
              \ifgrep@outopen
              \else
                 \immediate\openout\grep@outfile #3\relax
                 \immediate\write\grep@outfile{\p@rcent\space #3 %
                    -- generated automatically from #2}%
                 \immediate\write\grep@outfile{\p@rcent\space
                    Think twice before editing THIS file!}%
                 \grep@outopentrue
              \fi
              \immediate\write\grep@outfile{\grep@val}%
            \fi
          \fi
        \fi
      \ifgrep@cont
      \repeat
%    \end{macrocode}
% Close the files after we're done.
% \changes{1.1}{1994/05/16}{%
%   Stupid: {\tt closein} the input stream, don't use {\tt closeout} on it.}
%    \begin{macrocode}
      \ifgrep@outopen
        \immediate\closeout\grep@outfile
      \fi
    \fi
    \immediate\closein\grep@infile
  \endgroup}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\grep@infile}
%  \begin{macro}{\grep@outfile}
% The I/O streams for the grep facility
%    \begin{macrocode}
\newread\grep@infile
\newwrite\grep@outfile
%    \end{macrocode}
%  \end{macro}
% \end{macro}
% \begin{macro}{\ifgrep@cont}
%   \begin{macro}{\ifgrep@outopen}
% and flags for the same 
%    \begin{macrocode}
\newif\ifgrep@cont
\newif\ifgrep@outopen
%    \end{macrocode}
%   \end{macro}
% \end{macro}
%
% \begin{macro}{\grep@aline}
% Examine one line and set the variables |\grep@tag| and |\grep@val|
% iff the line starts with a colon.  Subtle point here: |\ifx#1:| will
% \emph{not} work if |#1| starts with a |{| followed by two identical
% characters.
%    \begin{macrocode}
\def\grep@aline#1#2\sentinel{%
  \ifx:#1%
    \grep@splitlbuf#2\sentinel
  \else
    \edef\grep@tag{\csname*grep*\endcsname}%
    \def\grep@val{}%
  \fi}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\grep@splitlbuf}
% Split the line buffer at the remaining colon, hashing the first part.
%    \begin{macrocode}
\def\grep@splitlbuf#1:#2\sentinel{%
  \edef\grep@tag{\csname*grep*#1*\endcsname}%
  \def\grep@val{#2}}
%</!mp>
%    \end{macrocode}
% \end{macro}
%
% The other \TeX{} command sequences are defined below, along with the
% \MF{} macros they are in one-to-one correspondence to.
%    \begin{macrocode}
%</style>
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section{\MF{} macros}
% \label{sec:mf-code}
%
% Now we turn our attention to the \MF{}
% macros.
% \begin{dubious}
%   We should find a way (a hack) to index the
%   \MF{} macros with the |doc| option.
% \end{dubious}
% Because to name clashes, \FMF{} will not work if the |cmbase| is
% loaded.  Die with an useful error message:
% \changes{1.5}{1994/06/13}{Don't accept the Computer Modern Base.}
%    \begin{macrocode}
%<*base>
if known cmbase:
  errhelp
    "feynmf will only work with plain Metafont, as described in the book.";
  errmessage "feynmf: CMBASE detected.  Please use the PLAIN base.";
  forever:
    errmessage "No use in trying!  You'd better eXit now ...";
    errorstopmode;
  endfor
fi
%    \end{macrocode}
%
% Make the RCS revision number available for feature testing:
% \changes{1.1}{1994/05/20}{%
%   Handle arbitrary RCS revision strings.}
%    \begin{macrocode}
vardef parse_RCS (suffix RCS) (expr s) =
  save n, c;
  numeric n, RCS[];
  string c;
  RCS[0] := 0;
  for n = 1 upto length (s):
    c := substring (n-1,n) of s;
    exitif ((RCS[0] > 0) and (c = " "));
    if ((c = "0") or (c = "1") or (c = "2")
        or (c = "3") or (c = "4") or (c = "5")
        or (c = "6") or (c = "7") or (c = "8")
        or (c = "9")):
      if RCS[0] = 0:
        RCS[0] := 1;
        RCS[RCS[0]] := 0;
      fi
      RCS[RCS[0]] := 10 * RCS[RCS[0]] + scantokens (c);
    elseif c = ".":
      RCS[0] := RCS[0] + 1;
      RCS[RCS[0]] := 0;
    else:
    fi
  endfor
enddef;
%    \end{macrocode}
% Check that \LaTeX{} style and \MF{} macros are in sync:
%    \begin{macrocode}
vardef require_RCS_revision expr s =
  save n, TeX_rev, mf_rev;
  numeric n;
  parse_RCS (TeX_rev, s);
  parse_RCS (mf_rev, "1.10");
  for n = 1 upto min (2, TeX_rev[0], mf_rev[0]):
    if TeX_rev[n] > mf_rev[n]:
      errhelp
        "Your version of `feynmf.sty' is higher that of your `feynmf.mf'.";
      errmessage "feynmf: Metafont macros out of date";
    elseif TeX_rev[n] < mf_rev[n]:
      errhelp
        "Your version of `feynmf.mf' is higher that of your `feynmf.sty'.";
      errmessage "feynmf: LaTeX style out of date";
    fi
    exitif (TeX_rev[n] <> mf_rev[n]);
  endfor
enddef;
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{\MP{} Kludges}
%
% This \MP{} support is still kludgey, but it works and we're trying
% to prove a point.
% \changes{1.4}{1994/05/27}{Preliminary \MP{} support: mimic \MF.}
%    \begin{macrocode}
%<*mp>
vardef cullit = \ enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef beginchar (expr c, wd, ht, dp) =
  LaTeX_file := "";
  beginfig(c);
    w:=wd;
    h:=ht;
enddef;
string LaTeX_file;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef endchar =
  setbounds currentpicture to (0,0)--(w,0)--(w,h)--(0,h)--cycle;
  if LaTeX_file <> "":
    write EOF to LaTeX_file;
    LaTeX_file := "";
  fi
  endfig
enddef;
%    \end{macrocode}
%
% Sharped dimensions are useless with \MP.  We define them anyway
% with trivial translation, so that the \MF{} code can be used
% unchanged.
%    \begin{macrocode}
bp# := bp;
cc# := cc;
cm# := cm;
dd# := dd;
in# := in;
mm# := mm;
pc# := pc;
pt# := pt;
%    \end{macrocode}
% As I said: trivial translation.
%    \begin{macrocode}
vardef define_blacker_pixels(text t) =
  forsuffixes $=t:
    $:=$.#;
  endfor
enddef;
%</mp>
%    \end{macrocode}
%
%    \begin{macrocode}
%<!mp>mode_setup;
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Basics}
% \label{sec:mf-basics}
%
% Allow the user to life dangerously or not, depending on his
% preferences.
% \changes{1.7}{1994/10/23}{\texttt{fmfwizard}: to live dangerously or not.}
%    \begin{macrocode}
boolean feynmfwizard;
feynmfwizard := false;
%</base>
%    \end{macrocode}
% \begin{macro}{\fmfwizard}
%   \begin{macro}{\fmfnowizard}
%    \begin{macrocode}
%<*style>
\def\fmfwizard{\fmfcmd{feynmfwizard := true;}}
\def\fmfnowizard{\fmfcmd{feynmfwizard := false;}}
%</style>
%    \end{macrocode}
%   \end{macro}
% \end{macro}
%
% Default values of style parameters:
%    \begin{macrocode}
%<*base>
thin#:=1pt#; % dimension of the lines
thick#:=2thin#;
arrow_len# := 4mm#;
arrow_ang := 15;
curly_len#:=3mm#;
dash_len#:=3mm#; % 'photon' lines
dot_len#:=2mm#; % 'photon' lines
wiggly_len#:=4mm#; % 'photon' lines
wiggly_slope:=60;
shade_black#:=1pt#; % shading
shade_white#:=2shade_black#;
shade_angle:=60;
decor_size#:=5mm#;
dot_size#:=2thick#;
%    \end{macrocode}
% Convert ``sharp'' units:
%    \begin{macrocode}
define_blacker_pixels (thick, thin, shade_black, shade_white,
  dash_len, dot_len, wiggly_len, curly_len, arrow_len,
  decor_size, dot_size);
%    \end{macrocode}
%
% Back by popular demand: shrinking dimensions.
% \changes{1.5}{1994/06/13}{%
%   Back by popular demand: shrinking dimensions.}
%    \begin{macrocode}
def shrink expr s =
  begingroup
  if shrinkables <> "":
    save tmp_;
    forsuffixes $ = scantokens shrinkables:
      tmp_ := $.#;
      save $;
      $.# := s * tmp_;
    endfor
    define_blacker_pixels (scantokens shrinkables);
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
def endshrink =
  endgroup
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfshrink}
%   \begin{macro}{\endfmfshrink}
% Exporting the whole enchilada to \LaTeX:
%    \begin{macrocode}
%<*style>
\def\fmfshrink#1{\fmfcmd{shrink (#1);}}
\def\endfmfshrink{\fmfcmd{endshrink;}}
%</style>
%    \end{macrocode}
%   \end{macro}
% \end{macro}
%
%    \begin {macrocode}
%<*base>
string shrinkables;
shrinkables := "";
%    \end{macrocode}
%
% This macro is used to register shrinkable dimensions.  It is not
% really robust, we have add the first enty by hand:
%    \begin {macrocode}
vardef addto_shrinkables (text l) =
  forsuffixes $ = l:
    shrinkables := shrinkables & "," & str $;
  endfor
enddef;
shrinkables := "thick,thin";
%    \end{macrocode}
%
%    \begin {macrocode}
addto_shrinkables (shade_black, shade_white);
addto_shrinkables (dash_len, dot_len);
addto_shrinkables (wiggly_len, curly_len);
addto_shrinkables (arrow_len);
addto_shrinkables (decor_size, dot_size);
%    \end{macrocode}
%
% Default to metric units, but this will be reset by |\begin{fmfchar}|
% anyway.
%    \begin {macrocode}
LaTeX_unitlength := mm;
%    \end{macrocode}
%
% Count the number of tokens in the argument:
%    \begin {macrocode}
vardef count (text list) =
  forsuffixes $ = list: + 1 endfor
enddef;
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Parsing options}
% \label{sec:getopt}
%
% Parse the string |s| into comma separated tokens |opt[]|, ignoring
% blanks before |=|'s. Double commas are passed as a single comma.
% \changes{1.9}{1994/10/25}{%
%   Plugged the string memory leak in \texttt{getopt}: don't create
%   intermediate one character strings, \MF{} never claims them back.}
%    \begin {macrocode}
vardef getopt (suffix opt) (expr s) =
  save n, argp, escape, anchor, skip;
  numeric opt.first, opt.last, n, anchor;
  string opt[], opt[]arg;
  boolean opt[]tainted, argp, escape, skip;
  opt.first := 0;
  opt.last := 0;
  opt[opt.last] := "";
  argp := false;
  escape := false;
  anchor := 0;
  skip := true;
  for n = 1 upto length (s):
%    \end{macrocode}
% Skip blanks at the beginning of each option or argument:
%    \begin {macrocode}
    if skip and (substring (n-1, n) of s = " "):
      anchor := anchor + 1;
    else:
      skip := false;
%    \end{macrocode}
% If we see a comma which has not been escaped, check for a second
% comma and set the |escape| flags and remember to remove the second
% comma later or reset the |argp| flag, as appropriate:
%    \begin {macrocode}
      if not escape and (substring (n-1, n) of s = ","):
        if substring (n, n+1) of s = ",":
          escape := true;
          opt[opt.last]tainted := true;
%    \end{macrocode}
% Else accept the option or argument:
%    \begin {macrocode}
        else:
          if argp:
            opt[opt.last]arg := substring (anchor, n-1) of s;
          else:
            opt[opt.last] := substring (anchor, n-1) of s;
          fi
          anchor := n;
          argp := false;
          skip := true;
          opt.last := opt.last + 1;
        fi
%    \end{macrocode}
% Start as argument and ignore |=|'s until the next option:
%    \begin {macrocode}
      elseif not argp and (substring (n-1, n) of s = "="):
        opt[opt.last] := substring (anchor, n-1) of s;
        anchor := n;
        argp := true;
        skip := true;
%    \end{macrocode}
% Accept the next character (either option or argument) and reset the
% |escape| flag:
%    \begin {macrocode}
      elseif argp or (substring (n-1, n) of s <> " "):
        escape := false;
      fi
    fi
  endfor
%    \end{macrocode}
% Accept the final option or argument:
%    \begin {macrocode}
  if argp:
    opt[opt.last]arg := substring (anchor, length s) of s;
  else:
    opt[opt.last] := substring (anchor, length s) of s;
  fi
%    \end{macrocode}
% We still have to remove possible doubled commata from the arguments.
% Theoretically, we could already have done it above (that's the way
% earlier versions of \FMF{} did it), but only at the expense of
% excessive copying of strings (like |opt[n]arg:=opt[n]arg&c|).  Given
% \MF's string handling, we should avoid these \emph{at any cost},
% because the wasted string memory will \emph{never} be
% reclaimed!\footnote{Actually, \MP{} has code to compact the string
%   pool, which  makes \emph{a lot} of difference in the present case.
%   But this doesn't help us with \MF.}
% Since the more elegant former version had a serious string memory
% leak, we'd better stick to the current ugly but space efficient
% implementation.
%    \begin {macrocode}
  for n = opt.first upto opt.last:
    if known opt[n]tainted:
      if opt[n]tainted:
        opt[n]arg := untaint_string opt[n]arg;
      fi
    fi
  endfor
enddef;
%    \end{macrocode}
% Turn double commata into single commata, using as little string
% copies as possible:
%    \begin {macrocode}
vardef untaint_string suffix s =
  save n, anchor;
  numeric n, anchor;
  anchor := 0;
  for n = 1 upto length (s) - 1:
    if substring (n-1,n+1) of s = ",,":
      substring (anchor, n-1) of s &
      hide (anchor := n)
    fi
  endfor
  substring (anchor, length s) of s
enddef;
%    \end{macrocode}
%
% Split a string into |.|-separated components for matching options.
%    \begin {macrocode}
vardef split_string (suffix comp) (expr s) =
  save n, anchor;
  numeric comp.first, comp.last, n, anchor;
  string comp[];
  comp.first := 0;
  comp.last := 0;
  comp[comp.last] := "";
  anchor := 0;
  for n = 1 upto length (s):
    if substring (n-1,n) of s = ".":
      comp[comp.last] := substring (anchor, n-1) of s;
      comp.last := comp.last + 1;
      anchor := n;
    fi
  endfor
  comp[comp.last] := substring (anchor, length s) of s;
enddef;
%    \end{macrocode}
% Return |true| iff |prefix| is a prefix of |s|:
%    \begin {macrocode}
vardef match_prefix (expr prefix, s) =
  (prefix = substring (0, length prefix) of s)
enddef;
%    \end{macrocode}
% Match options similarly to |Xt| resource strings, but allowing for
% abbreviations:
% \changes{1.7}{1994/10/23}{More general option parsing.}
%    \begin {macrocode}
vardef match_option (expr s, option) =
  save sc, optionc, n, i;
  numeric sc.first, sc.last, optionc.first, optionc.last;
  string sc[], optionc[];
  numeric n, i;
  split_string (sc, s);
  split_string (optionc, option);
  n := sc.last - sc.first;
  if n <> (optionc.last - optionc.first):
    false
  else:
    true
    for i = 0 upto n:
      and match_prefix (sc[sc.first+i],
                        optionc[optionc.first+i])
    endfor
  fi
enddef;
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Manipulating \texttt{picture}s}
% \label{sec:pictures}
%
% |save_picture (list_of_pictures)| |save|'s each member of
% |list_of_pictures| inside a group and reinitializes them as nullpictures.
%    \begin{macrocode}
def save_picture text t =
 save t; picture t; forsuffixes p=t: p:=nullpicture; endfor
enddef;
%    \end{macrocode}
%
% |begin_sketch| pushes the sketchpad stack and perform the following
% drawing commands (upto the next |end_sketch|) on the new sketchpad.
%    \begin{macrocode}
def begin_sketch =
 begingroup save_picture currentpicture;
 sketchlevel := sketchlevel+1;
enddef;
%    \end{macrocode}
%
% |end_sketch| pops the sketchpad stack.
%    \begin{macrocode}
def end_sketch =
 sketchlevel := sketchlevel-1;
 sketchpad[sketchlevel] := currentpicture;
 endgroup
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
picture sketchpad[];
sketchlevel := 1;
%    \end{macrocode}
%
% |use_sketch (transformation)| copies the transformed sketchpad into
% the current picture.
%    \begin{macrocode}
vardef use_sketch text t =
 addto currentpicture also (sketchpad[sketchlevel] t)
enddef;
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Shading}
% \label{sec:shading}
%
% |shade (path_arg)| shades the interior of |path_arg|.  This shading is
% controlled by the global variables |shade_black|, |shade_white|, and
% |shade_angle|.
% Caveat:  The procedure is only guaranteed to work for convex paths.
% \begin{dubious}
%   \MP{} has nice primitives to aid in finding bounding boxes, in
%   \MF{} we have to rely on heuristics.
% \end{dubious}
%    \begin{macrocode}
vardef shade expr p_arg =
 save x,y,d,p,currentpen; path p; pen currentpen;    % push pen!
 pickup pencircle scaled shade_black;
 p = p_arg rotated - shade_angle;  % calculate enclosing rectangle
 x2' = x3' = xpart directionpoint up of p; % (rotated by |shade_angle|).
 x1' = x4' = xpart directionpoint down of p;
 y1' = y2' = ypart directionpoint right of p;
 y3' = y4' = ypart directionpoint left of p;
 forsuffixes $=1,2,3,4: z$ = z$' rotated shade_angle; endfor
 d = abs(z1-z4); % height.
 begin_sketch % fill rectangle with lines.
  for k=shade_white/d step (shade_white+shade_black)/d
    until 1 - shade_white/d:
   cutdraw k[z1,z4] -- k[z2,z3];
  endfor
%    \end{macrocode}
% \MF{} has no clipping operation, but since we know the bounding box,
% we can use \MF's pixel arithmetic for calculating the set
% theoretical intersection of the interior of |p_arg| and the diagonal
% lines in the bounding box:
%    \begin{macrocode}
%<*!mp>
  cullit;
  fill p_arg;
  unfill z1--z2--z3--z4--cycle;
  cullit;
%</!mp>
%    \end{macrocode}
% \MP{} has clipping build in but no pixel arithmetic:
% \changes{1.4}{1994/05/28}{\MP{} support: shading.}
%    \begin{macrocode}
%<*mp>
  clip currentpicture to p_arg;
%</mp>
 end_sketch;
 use_sketch;
enddef;
%    \end{macrocode}
%
% Hatching is implemented as double shading.
% \changes{1.7}{1994/10/22}{Hatched vertices.}
%    \begin{macrocode}
vardef hatch expr p =
  shade p;
  save a;
  a = shade_angle;
  save shade_angle;
  shade_angle = a + 90;
  shade p;
enddef;
%    \end{macrocode}
%
% |filldraw|'s sisters:
%    \begin{macrocode}
vardef shadedraw expr p =
  shade p;
  draw p;
enddef;
vardef hatchdraw expr p =
  hatch p;
  draw p;
enddef;
%    \end{macrocode}
%
% John Hobby has a particulary nice |arrowhead| macro in plain \MP.  A
% variation on that theme adapted to our needs is:
% \changes{1.5}{1994/10/20}{New arrows, which look better on curved arcs.}
%    \begin{macrocode}
vardef arrow expr p =
  save t, a, z_, ap_, tip;
  numeric t[], a;
  pair z_, tip;
  path ap_;
  a = angle direction .5 length(p) of p;
  z_ = point .5 length(p) of p;
  (t1,whatever) = p intersectiontimes
    (halfcircle scaled 2/3arrow_len rotated (a+90) shifted z_);
  (t2,whatever) = p intersectiontimes
    (halfcircle scaled 4/3arrow_len rotated (a-90) shifted z_);
%    \end{macrocode}
% |intersectiontimes| can fail, typically if the path is too short:
% protect against it
% \changes{1.6}{1994/10/21}{Fix arrows on too short arcs.}
%    \begin{macrocode}
  if t1 = -1: t1 := 0; fi
  if t2 = -1: t2 := length p; fi
  tip = point t2 of p;
  ap_ = subpath (t1,t2) of p shifted -tip;
  (ap_ rotated arrow_ang
    forced_join reverse ap_ rotated -arrow_ang
    -- cycle) shifted tip
enddef;
%    \end{macrocode}
% Join two paths |p| and |q| even if they don't fit exactly by
% adjusting their common point.  This is necessary in |arrow| because
% rounding errors might induce a small mismatch even if we \emph{know}
% that they should match theoretically.  This is certainly a kludge
% and should be used with care, but it works.
%    \begin{macrocode}
tertiarydef p forced_join q =
  subpath (0, length p - 1) of p
  & point (length p - 1) of p
    .. controls postcontrol (length p - 1) of p
                and precontrol infinity of p
  .. .5[point infinity of p, point 0 of q]
    .. controls postcontrol 0 of q and precontrol 1 of q
    .. point 1 of q
  & subpath (1, infinity) of q
enddef;
%    \end{macrocode}
%
% |cut_decors| expands to a subpath of |path_arg|, excluding the
% decoration at the vertices.
% \changes{1.7}{1994/10/22}{Cut general vertex decorations.}
%    \begin{macrocode}
vardef cut_decors (suffix from) (expr p) (suffix to) =
 subpath (if known from.decor.shape:
            xpart (p intersectiontimes
                     (from.decor.shape scaled from.decor.size
                                       shifted from.loc))
          else:
            0
          fi,
          if known to.decor.shape:
            xpart (p intersectiontimes
                     (to.decor.shape scaled to.decor.size
                                     shifted to.loc))
         else:
            infinity
         fi) of p
enddef;
%    \end{macrocode}
%
% The function |make_blob| is the working horse of |draw_blob|.
%    \begin{macrocode}
vardef make_blob (expr z_arg, diameter) =
 save p,currentpen; path p; pen currentpen;
 pickup pencircle scaled thick;
 p = fullcircle scaled diameter shifted z_arg;
 shadedraw p;
enddef;
%    \end{macrocode}
%
% |draw_blob (pair_arg, diameter)| draws a shaded blob of diameter
% |diameter| centered at |pair_arg|. The thickness of the border is
% controlled by the global variable |thick|.
%
% Hint: It saves time to draw blobs of the same size in sequence.
%    \begin{macrocode}
vardef draw_blob (expr z_arg, diameter) =
 if sketched_blob_diameter <> diameter: % drawn lately?
  begin_sketch make_blob (origin, diameter); end_sketch; % redo hard work!
  sketched_blob_diameter:= diameter;  % record it
 fi
 use_sketch shifted z_arg; % the easy way ...
enddef;
%    \end{macrocode}
%
% |force_new_blob| forces the redrawing of a blob of the same diameter
% (in case you only changed the shading parameters).
%    \begin{macrocode}
def force_new_blob = sketched_blob_diameter := -1; enddef;
force_new_blob;                                 % initialize it.
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Drawing}
% \label{sec:drawing}
%
% Easier than
% \begin{equation}
%   \int_0^1 dt \left\vert\frac{dx(t)}{dt}\right\vert
% \end{equation}
% with the integrand the square root of a fourth order polynomial, but
% sufficient for all practical purposes is
%    \begin{macrocode}
vardef pixlen (expr p, n) =
  for k=1 upto length(p): + segment_pixlen (subpath (k-1,k) of p, n) endfor
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef segment_pixlen (expr p, n) =
  for k=1 upto n: + abs (point k/n of p - point (k-1)/n of p) endfor
enddef;
%    \end{macrocode}
%
% |wiggly (path_arg)| expands to a ``wiggled'' version of |path_arg|. The
% slope of the wiggles is controlled by the global variable |wiggle_slope|,
% the length of the wiggles by the global variable |wiggly_len|.
%    \begin{macrocode}
vardef wiggly expr p_arg =
 save wpp;
 numeric wpp;
 wpp = ceiling (pixlen (p_arg, 10) / (wiggly_len * length(p_arg)));
 for k=0 upto wpp*length(p_arg) - 1:
  point k/wpp of p_arg
       {direction k/wpp of p_arg rotated wiggly_slope} ..
  point (k+.5)/wpp of p_arg
       {direction (k+.5)/wpp of p_arg rotated - wiggly_slope} ..
 endfor
 if cycle p_arg: cycle else: point infinity of p_arg fi
enddef;
%    \end{macrocode}
%

% |curly (path_arg)| expands to a ``curly'' version of |path_arg|. The
% the length of the curls is controlled  by the global variable
% |curly_len|.
%    \begin{macrocode}
vardef curly expr p_arg =
 save cpp;
 numeric cpp;
 cpp = ceiling (pixlen (p_arg, 10) / (curly_len * length(p_arg)));
 if cycle p_arg:
   for k=0 upto cpp*length(p_arg) - 1:
     point (k+.33)/cpp of p_arg
           {direction (k+.33)/cpp of p_arg rotated 90} ..
     point (k-.33)/cpp of p_arg
           {direction (k-.33)/cpp of p_arg rotated -90} ..
   endfor
   cycle
 else:
   point 0 of p_arg
         {direction 0 of p_arg rotated -90} ..
   for k=1 upto cpp*length(p_arg) - 1:
     point (k+.33)/cpp of p_arg
           {direction (k+.33)/cpp of p_arg rotated 90} ..
     point (k-.33)/cpp of p_arg
           {direction (k-.33)/cpp of p_arg rotated -90} ..
   endfor
   point infinity of p_arg
         {direction infinity of p_arg rotated 90}
 fi
enddef;
%    \end{macrocode}
%
% An inventory of valid line styles is implemented as a hash table:
%    \begin{macrocode}
save vsty_hash;
%    \end{macrocode}
% This is a bit like |mode_def| in plain \MF{} but doesn't use an
% array of available modes: |style_def "foo"| will define a macro
% |draw_foo| drawing a line of a certain style along any given path:
%    \begin{macrocode}
def style_def suffix s =
  vsty_hash.s := 1;
  expandafter quote vardef scantokens ("draw_" & str s)
enddef;
%    \end{macrocode}
%
% Let \MF{} do the lookup: suffices
%    \begin{macrocode}
vardef vsty_exists suffix s =
  known vsty_hash.s
enddef;
%    \end{macrocode}
% an strings
%    \begin{macrocode}
vardef valid_style expr s =
  expandafter vsty_exists scantokens (s)
enddef;
%    \end{macrocode}
%
% \changes{1.9}{1994/11/21}{Enhance and streamline the line styles.}
% |phantom| lines are simple, even with arrows.
%    \begin{macrocode}
style_def phantom expr p =
  \
enddef;
style_def phantom_arrow expr p =
  fill (arrow p);
enddef;
%    \end{macrocode}
% |plain| lines aren't harder.
%    \begin{macrocode}
style_def plain expr p =
  draw p;
enddef;
style_def plain_arrow expr p =
  draw p;
  fill (arrow p);
enddef;
style_def dbl_plain expr p =
  draw_double p;
enddef;
style_def dbl_plain_arrow expr p =
  draw_double_arrow p;
enddef;
%    \end{macrocode}
% Wiggly lines use |wiggly| from above
%    \begin{macrocode}
style_def wiggly expr p =
  draw (wiggly p);
enddef;
style_def dbl_wiggly expr p =
  draw_double (wiggly p);
enddef;
%    \end{macrocode}
% and curly lines use |curly| from above
%    \begin{macrocode}
style_def curly expr p =
  draw (curly p);
enddef;
style_def dbl_curly expr p =
  draw_double (curly p);
enddef;
%    \end{macrocode}
% |draw_dashes (p)| draws a dashed line on |p|
% \changes{1.4}{1994/05/27}{%
%   Rename the line style \texttt{dashed} to \texttt{dashes}, to avoid
%   a name clash with \MP.}
%    \begin{macrocode}
style_def dashes expr p_arg =
 save dpp;
 numeric dpp;
 dpp = ceiling (pixlen (p_arg, 10) / (dash_len * length(p_arg)));
 for k=0 upto dpp*length(p_arg) - 1:
  draw point k/dpp of p_arg ..
   point (k+.5)/dpp of p_arg;
 endfor
enddef;
style_def dbl_dashes expr p =
 save dpp;
 numeric dpp;
 dpp = ceiling (pixlen (p, 10) / (dash_len * length(p)));
 for k=0 upto dpp*length(p) - 1:
  draw_double point k/dpp of p ..
   point (k+.5)/dpp of p;
 endfor
enddef;
style_def dbl_dashes_arrow expr p =
  draw_dbl_dashes p;
  fill (arrow p);
enddef;
style_def dashes_arrow expr p =
  draw_dashes p;
  fill (arrow p);
enddef;
%    \end{macrocode}
%
% |draw_dots (expr p_arg)| draws a dotted line on |path_arg|
% \changes{1.4}{1994/05/27}{%
%   Rename the line style \texttt{dotted} to \texttt{dots}, to be
%   consistent with \texttt{dashes}.}
%    \begin{macrocode}
style_def dots expr p_arg =
 save dpp;
 numeric dpp;
 dpp = ceiling (pixlen (p_arg, 10) / (dot_len * length(p_arg)));
 for k=0 upto dpp*length(p_arg):
  drawdot point k/dpp of p_arg;
 endfor
enddef;
style_def dbl_dots expr p_arg =
  save dpp;
  numeric dpp;
  dpp = ceiling (pixlen (p_arg, 10) / (dot_len * length(p_arg)));
  begingroup
    pen oldpen;
    oldpen := currentpen;
    pickup oldpen scaled 3; % draw a thick linn
    for k=0 upto dpp*length(p_arg):
      drawdot point k/dpp of p_arg;
    endfor
    pickup oldpen;
    cullit;
    for k=0 upto dpp*length(p_arg):
      undrawdot point k/dpp of p_arg;
    endfor
    cullit; % and remove the stuffing
  endgroup;
enddef;
style_def dbl_dots_arrow expr p =
  draw_dbl_dots p;
  fill (arrow p);
enddef;
style_def dots_arrow expr p =
  draw_dots p;
  fill (arrow p);
enddef;
%    \end{macrocode}
%
% |draw_double (expr p_arg)| draws a double line.
%    \begin{macrocode}
style_def double expr p_arg =
  begingroup
    pen oldpen;
    oldpen := currentpen;
    pickup oldpen scaled 3; % draw a thick linn
    draw p_arg;
    pickup oldpen;
    cullit; undraw p_arg; cullit; % and remove the stuffing
  endgroup;
enddef;
style_def double_arrow expr p =
  draw_double p;
  fill (arrow p);
enddef;
%    \end{macrocode}
%
% Old aliases:
%    \begin{macrocode}
style_def vanilla expr p = draw_plain p enddef;
style_def fermion expr p = draw_plain_arrow p enddef;
style_def quark expr p = draw_plain_arrow p enddef;
style_def electron expr p = draw_plain_arrow p enddef;
style_def photon expr p = draw_wiggly p enddef;
style_def boson expr p = draw_wiggly p enddef;
style_def gluon expr p = draw_curly p enddef;
style_def heavy expr p = draw_dbl_plain_arrow p enddef;
style_def ghost expr p = draw_dots_arrow p enddef;
style_def scalar expr p = draw_dashes_arrow p enddef;
%    \end{macrocode}
% More old aliases:
%    \begin{macrocode}
vardef fermion expr path_arg =
  fill arrow (path_arg);
  path_arg
enddef;
vardef photon expr path_arg =
  wiggly path_arg
enddef;
vardef gluon expr path_arg =
  curly path_arg
enddef;
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsection{Graphs of vertices}
% \label{sec:graphs}
%
% Here is the fun part of \FMF: \emph{automagic} placement of
% vertices.
%    \begin{macrocode}
%tracingmacros:=1;
%tracingonline:=1;
tracingstats:=1;
%    \end{macrocode}
%
% You can say |vtracing:=true| to see what's going on.
%    \begin{macrocode}
boolean vtracing;
vtracing := false; % true
%    \end{macrocode}
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Data structures}
%
% \begin{table}
%   \begin{tabular}{lll}
%     Type      & Name          & Purpose \\\hline
%     |numeric| & |vlist.first| & pointer to first vertex (usually 1) \\
%     |numeric| & |vlist.last|  & pointer to last vertex (starts with 0) \\
%     |string|  & |vlist[|$i$|]name|          & symbolic name of the vertex\\
%     |pair|    & |vlist[|$i$|]loc|           & position of the vertex \\
%     |string|  & |vlist[|$i$|]lbl|           & label \\
%     |numeric| & |vlist[|$i$|]lbl.ang|       & angle \\
%     |numeric| & |vlist[|$i$|]lbl.dist|      & distance \\
%     |path|    & |vlist[|$i$|]decor.shape|   & shape of decoration\\
%     |numeric| & |vlist[|$i$|]decor.size|    & size of decoration\\
%     |numeric| & |vlist[|$i$|]decor.sty|     & filling style of decoration\\
%     |numeric| & |vlist[|$i$|]decor.ang|     & rotation angle\\
%     |numeric| & |vlist[|$i$|]arc.first|     & pointer to first arc \\
%     |numeric| & |vlist[|$i$|]arc.last|      & pointer to last arc \\
%     |numeric| & |vlist[|$i$|]arc[|$j$|]|    & $j$th arc of the $i$th vertex \\
%     |string|  & |vlist[|$i$|]arc[|$j$|]sty| & style of the arc\\
%     |numeric| & |vlist[|$i$|]arc[|$j$|]tns| & tension of the arc\\
%     |string|  & |vlist[|$i$|]arc[|$j$|]lsr| & left, straight, right\\
%     |string|  & |vlist[|$i$|]arc[|$j$|]lbl| & label\\
%     |string|  & |vlist[|$i$|]arc[|$j$|]lbl.side|& side of the label\\
%     |numeric| & |vlist[|$i$|]arc[|$j$|]lbl.dist|& distance of the label
%   \end{tabular}
%   \caption{Vertex data structure}
%   \label{tab:VDS}
% \end{table}
% The data structure for our graph is shown in
% table~\ref{tab:VDS}\footnote{%
%   \begin{dubious}
%     \texttt{boolean vlist[i]arc[j]smooth} will indicate that this
%     arc belongs to a set of arcs which are to be smoothly connected.
%     The implementation will start by going to the strt of this set,
%     define a long smooth path and finally do the drawing on the
%     various subpaths.
%   \end{dubious}}.
% \MF{} turns out to be quite powerful, providing such constructs
% in an unconventional, but flexible and concise way.  While we use
% |save vhash| to forget all previously defined vertices, we leave
% |vlist| alone, because we will know from $|vlist.last| <
% |vlist.first|$ that it's empty.  Note that we can't |vardef| this
% because then the |save| would go inside a group.
%    \begin{macrocode}
def vinit =
  save vhash;
  numeric vlist.first, vlist.last;
  vlist.first := 1;
  vlist.last := 0;
  pair vlist[]loc, lambda[][];
  numeric vlist[]decor.size, vlist[]decor.sty, vlist[]decor.ang,
    vlist[]arc.first, vlist[]arc.last,
    vlist[]arc[], vlist[]arc[]lsr,
    vlist[]arc[]tns, vlist[]arc[]lbl.dist,
    vlist[]constr.first, vlist[]constr.last,
    vlist[]constr[];
  string vlist[]name, vlist[]lbl,
    vlist[]arc[]sty, vlist[]arc[]lbl, vlist[]arc[]lbl.side;
  numeric vlist[]lbl.ang, vlist[]lbl.side;
  path vlist[]decor.shape;
enddef;
%</base>
%    \end{macrocode}
% \begin{macro}{\fmfinit}
% We can also ask for initialization explicitely from \TeX{} (usually
% it is called implicitely by |\begin{fmfchar}|).  This flushes the
% vertex table. 
%    \begin{macrocode}
%<style>\def\fmfinit{\fmfcmd{vinit;}}
%    \end{macrocode}
% \end{macro}
% Useful abstractions are: first for looping over all vertices
%    \begin{macrocode}
%<*base>
def vertices =
  vlist.first upto vlist.last
enddef;
%    \end{macrocode}
% second for looping over all arcs of vertex |i|
%    \begin{macrocode}
def varcs (text i) =
  vlist[i]arc.first upto vlist[i]arc.last
enddef;
%    \end{macrocode}
% and finally for looping over all constraints of vertex |i|
%    \begin{macrocode}
def vconstr (text i) =
  vlist[i]constr.first upto vlist[i]constr.last
enddef;
%    \end{macrocode}
% Entering vertices is simple, but note that we have to make
% |vlist[|$i$|]loc| undefined, because it might be around from an
% earlier character still.
%    \begin{macrocode}
vardef venter suffix v =
  if not vexists v:
    vlist.last := vlist.last + 1;
    vhash.v := vlist.last;
    vlist[vhash.v]name := str v;
    vlist[vhash.v]loc := (whatever,whatever);
    vlist[vhash.v]arc.first := 1;
    vlist[vhash.v]arc.last := 0;
    vlist[vhash.v]constr.first := 1;
    vlist[vhash.v]constr.last := 0;
    vlist[vhash.v]lbl := "";
    vlist[vhash.v]lbl.ang := whatever;
    vlist[vhash.v]lbl.dist := 3;
  fi
enddef;
%    \end{macrocode}
%
% The next three \emph{are} trivial. Existence
%    \begin{macrocode}
vardef vexists suffix v =
  if known vhash.v: true else: false fi
enddef;
%    \end{macrocode}
% index
%    \begin{macrocode}
vardef vlookup suffix v =
  if vexists v: vhash.v else: 0 fi
enddef;
%    \end{macrocode}
% and location
%    \begin{macrocode}
vardef vloc suffix v =
  vlist[vlookup v]loc
enddef;
%    \end{macrocode}
% of vertices.  We use |vhash.v| instead of |v| so that we can clear
% the whole hash table with |save vhash|.
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Constructing the Graph}
%
% Connect the vertices in the list |vl| with lines of style |style|,
% allocating them if necessary.
% \begin{dubious}
%   Be more flexible about whether adding arrows
%   or not.  This should be implemented using the options and devising
%   a path filter mechanism.
% \end{dubious}
%    \begin{macrocode}
vardef vconnect (expr linesty) (text vl) =
  save from, nfrom, nto, nopt, sty;
  numeric from, nfrom, nto, nopt;
  string sty;
  getopt (opt, linesty);
  sty := opt[opt.first];
  if known opt[opt.first]arg:
    message "feynmf: line styles don't take arguments.  "
             & "Argument `" & opt[opt.first]arg & "' ignored.";
  fi
  opt.first := opt.first + 1;
  forsuffixes to = vl:
    venter to;
    nto := vlookup to;
    if known nfrom:
%    \end{macrocode}
% Later, on page~\pageref{pg:vposition}, it will pay back to enter the
% arc \emph{both} ways: incoming \emph{and}
% outgoing:\label{pg:vconnect}
%    \begin{macrocode}
      vlist[nfrom]arc.last := vlist[nfrom]arc.last + 1;
      vlist[nto]arc.last := vlist[nto]arc.last + 1;
      vlist[nfrom]arc[vlist[nfrom]arc.last] := nto;
      vlist[nto]arc[vlist[nto]arc.last] := nfrom;
      vlist[nfrom]arc[vlist[nfrom]arc.last]tns := 1;
      vlist[nto]arc[vlist[nto]arc.last]tns := 1;
      vlist[nfrom]arc[vlist[nfrom]arc.last]lsr := 0;
      vlist[nfrom]arc[vlist[nfrom]arc.last]lbl := "";
      vlist[nfrom]arc[vlist[nfrom]arc.last]lbl.side := "";
      vlist[nfrom]arc[vlist[nfrom]arc.last]lbl.dist := 3;
%    \end{macrocode}
% Handle options, starting with an option |tension|:
%    \begin{macrocode}
      for nopt = opt.first upto opt.last:
        if match_option (opt[nopt], "tension"):
          get_argument (opt[nopt], scantokens (opt[nopt]arg),
                        vlist[nfrom]arc[vlist[nfrom]arc.last]tns);
          get_argument (opt[nopt], scantokens (opt[nopt]arg),
                        vlist[nto]arc[vlist[nto]arc.last]tns);
%    \end{macrocode}
% Handle |left|, |straight| and |right|, which ask for making a
% halfcircle detour on the specified side or going straight.  If given
% an optional argument, the halfcircle is pulled in or pushed out,
% according whether it is smaller or larger than 1.
% \changes{1.5}{1994/10/20}{Accept optional argument for detours.}
%    \begin{macrocode}
        elseif match_option (opt[nopt], "left"):
          if known opt[nopt]arg:
            vlist[nfrom]arc[vlist[nfrom]arc.last]lsr
              := - scantokens (opt[nopt]arg);
          else:
            vlist[nfrom]arc[vlist[nfrom]arc.last]lsr := -1;
          fi
        elseif match_option (opt[nopt], "straight"):
          vlist[nfrom]arc[vlist[nfrom]arc.last]lsr := 0;
          ignore_argument (opt[nopt], opt[nopt]arg);
        elseif match_option (opt[nopt], "right"):
          if known opt[nopt]arg:
            vlist[nfrom]arc[vlist[nfrom]arc.last]lsr
              := scantokens (opt[nopt]arg);
          else:
            vlist[nfrom]arc[vlist[nfrom]arc.last]lsr := 1;
          fi
%    \end{macrocode}
% Labels and which side they're on:
%    \begin{macrocode}
        elseif match_option (opt[nopt], "label"):
          get_argument (opt[nopt], opt[nopt]arg,
                        vlist[nfrom]arc[vlist[nfrom]arc.last]lbl);
        elseif match_option (opt[nopt], "label.side"):
          get_argument (opt[nopt], opt[nopt]arg,
                        vlist[nfrom]arc[vlist[nfrom]arc.last]lbl.side);
        elseif match_option (opt[nopt], "label.dist"):
          get_argument (opt[nopt], scantokens (opt[nopt]arg),
                        vlist[nfrom]arc[vlist[nfrom]arc.last]lbl.dist);
%    \end{macrocode}
% Ignore bogus options:
%    \begin{macrocode}
        else:
          ignore_option (opt[nopt], opt[nopt]arg);
        fi
      endfor
%    \end{macrocode}
% Avoid entering invalid linestyles into the tables, because the
% delayed evaluation will make errors harder to find (line numbers
% will be wrong):
%    \begin{macrocode}
      if valid_style sty:
        vlist[nfrom]arc[vlist[nfrom]arc.last]sty := sty;
      else:
        errhelp "feynmf: your linestyle is not recognizable, "
              & "check spelling and reprocess!";
        errmessage "feynmf: line style `" & sty & "' not known, "
                 & "replaced by `vanilla'"; 
        vlist[nfrom]arc[vlist[nfrom]arc.last]sty := "vanilla";
      fi
    fi
%    \end{macrocode}
% Restart the loop:
%    \begin{macrocode}
    nfrom := nto;
  endfor
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef get_argument (expr opt, arg) (suffix variable) =
  if known arg:
    variable := arg;
  else:
    message "feynmf: option `" & opt & "' needs an argument.  Ignored.";
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef ignore_argument (expr opt, arg) =
  if known arg:
    message "feynmf: option `" & opt & "' doesn't take an argument.  "
          & "Argument `" & arg & "' ignored.";
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef ignore_option (expr opt, arg)=
  if known arg:
    message "feynmf: ignoring option " & opt & "=" & arg & ".";
  else:
    message "feynmf: ignoring option " & opt & ".";
  fi
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmf}
% Since |vconnect| wil be the most frequent macro, we give it the
% shortest \TeX{} command sequence:
%    \begin{macrocode}
%<style>\def\fmf#1#2{\fmfcmd{vconnect ("#1", #2);}}
%    \end{macrocode}
% \end{macro}
%
%    \begin{macrocode}
%<*base>
vardef vcyclen (expr sty) (suffix v) (expr n) =
  for $ = 1 upto n - 1:
    vconnect (sty, v[$], v[$+1]);
  endfor
  vconnect (sty, v[n], v[1]);
enddef;
%    \end{macrocode}
% And the reverse:
%    \begin{macrocode}
vardef vrcyclen (expr sty) (suffix v) (expr n) =
  vconnect (sty, v[1], v[n]);
  for $ = n downto 2:
    vconnect (sty, v[$], v[$-1]);
  endfor
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfcyclen}
%    \begin{macrocode}
%<style>\def\fmfcyclen#1#2#3{\fmfcmd{vcyclen ("#1", #2, #3);}}
%<style>\def\fmfrcyclen#1#2#3{\fmfcmd{vrcyclen ("#1", #2, #3);}}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmfforce}
%   \begin{macro}{\fmfshift}
% Explicit placement and shifting of vertices is handled in \TeX{} with
%    \begin{macrocode}
%<style>\def\fmfforce#1#2{\fmfcmd{vforce ((#1),#2);}}
%<style>\def\fmfshift#1#2{\fmfcmd{vshift((#1),#2);}}
%    \end{macrocode}
%   \end{macro}
% \end{macro}
%
% Force the vertex |v| to be placed at position |z|:
%    \begin{macrocode}
%<*base>
vardef vforce (expr z) (suffix v) =
  venter v;
  vlist[vlookup v]loc := z;
enddef;
%    \end{macrocode}
%
% Shift the vertex |v| by |z|:
%    \begin{macrocode}
vardef vshift (expr z) (text vl) =
  forsuffixes $=vl:
    if vexists $:
      vlist[vlookup $]loc := vlist[vlookup $]loc + z;
    fi
  endfor
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmffixed}
% \changes{1.9}{1995/01/07}{New command: \texttt{fmffixed}.}
% Place the first two arguments in the distance given by the third
% argument.
%    \begin{macrocode}
%<style>\def\fmffixed#1#2{\fmfcmd{vconstraint ((#1), #2);}}
%    \end{macrocode}
% \end{macro}
% This amounts to adding one or more constraints into the vertex data
% structure:
%    \begin{macrocode}
%<*base>
vardef vconstraint (expr z) (text vl) =
  save nfrom, nto;
  numeric nfrom, nto;
  forsuffixes to = vl:
    venter to;
    nto := vlookup to;
    if known nfrom:
      vlist[nfrom]constr.last := vlist[nfrom]constr.last + 1;
      vlist[nto]constr.last := vlist[nto]constr.last + 1;
      vlist[nfrom]constr[vlist[nfrom]constr.last] := nto;
      vlist[nto]constr[vlist[nto]constr.last] := nfrom;
      vlist[nto]loc = vlist[nfrom]loc + z;
    fi
    nfrom := nto;
  endfor
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmflabel}
%    \begin{macrocode}
%<style>\def\fmflabel#1#2{\fmfcmd{vlabel ("#1", #2);}}
%    \end{macrocode}
% \end{macro}
%
%    \begin{macrocode}
%<*base>
vardef vlabel (expr s) (suffix v) =
  venter v;
  vlist[vlookup v]lbl := s;
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfv}
%    \begin{macrocode}
%<style>\def\fmfv#1#2{\fmfcmd{vvertex ("#1", #2);}}
%<style>\def\fmfvn#1#2#3{\fmfcmd{vvertexn ("#1", #2, #3);}}
%    \end{macrocode}
% \end{macro}
%
% \changes{1.7}{1994/10/22}{%
%  \texttt{blob} and \texttt{dot} options obsolete, handle generalized
%  decorations (polygons).}
%    \begin{macrocode}
%<*base>
vardef vvertex (expr vtxsty) (text vl) =
  save nopt, sty, arg;
  numeric nopt, arg;
  string sty;
  getopt (opt, vtxsty);
  forsuffixes v = vl:
    venter v;
    n := vlookup v;
    for nopt = opt.first upto opt.last:
      if match_option (opt[nopt], "label"):
        get_argument (opt[nopt], opt[nopt]arg, vlist[n]lbl);
      elseif match_option (opt[nopt], "label.angle"):
        get_argument (opt[nopt], scantokens (opt[nopt]arg),
                      vlist[n]lbl.ang);
      elseif match_option (opt[nopt], "label.dist"):
        get_argument (opt[nopt], scantokens (opt[nopt]arg),
                      vlist[n]lbl.dist);
      elseif match_option (opt[nopt], "decoration.shape"):
        if known opt[nopt]arg:
%    \end{macrocode}
% Maybe we should replace the following long switch by a hashing
% scheme.
%    \begin{macrocode}
          if match_prefix (opt[nopt]arg, "circle"):
            vlist[n]decor.shape := fullcircle;
          elseif match_prefix (opt[nopt]arg, "square"):
            vlist[n]decor.shape := unitsquare shifted -(.5,.5);
          elseif match_prefix (opt[nopt]arg, "triangle"):
            vlist[n]decor.shape := polygon 3;
          elseif match_prefix (opt[nopt]arg, "triagon"):
            vlist[n]decor.shape := polygon 3;
          elseif match_prefix (opt[nopt]arg, "diamond"):
            vlist[n]decor.shape := polygon 4;
          elseif match_prefix (opt[nopt]arg, "tetragon"):
            vlist[n]decor.shape := polygon 4;
          elseif match_prefix (opt[nopt]arg, "pentagon"):
            vlist[n]decor.shape := polygon 5;
          elseif match_prefix (opt[nopt]arg, "hexagon"):
            vlist[n]decor.shape := polygon 6;
          elseif match_prefix (opt[nopt]arg, "triagram"):
            vlist[n]decor.shape := polygram 3;
          elseif match_prefix (opt[nopt]arg, "tetragram"):
            vlist[n]decor.shape := polygram 4;
          elseif match_prefix (opt[nopt]arg, "pentagram"):
            vlist[n]decor.shape := polygram 5;
          elseif match_prefix (opt[nopt]arg, "hexagram"):
            vlist[n]decor.shape := polygram 6;
          else:
            if feynmfwizard:
              vlist[n]decor.shape := scantokens(opt[nopt]arg);
            else:
              message "feynmf: invalid argument `" & opt[nopt]arg
                    & "' to option `decor.shape'.  Ignored.";
            fi
          fi
        else:
          message "feynmf: option `decor.shape' needs an argument.  Ignored.";
        fi
%    \end{macrocode}
% \MP{} has |filled| reserved, use |sty| instead.
%    \begin{macrocode}
      elseif match_option (opt[nopt], "decoration.filled"):
        get_argument (opt[nopt], scantokens (opt[nopt]arg),
                      vlist[n]decor.sty);
      elseif match_option (opt[nopt], "decoration.size"):
        get_argument (opt[nopt], scantokens (opt[nopt]arg),
                      vlist[n]decor.size);
      elseif match_option (opt[nopt], "decoration.angle"):
        get_argument (opt[nopt], scantokens (opt[nopt]arg),
                      vlist[n]decor.ang);
%    \end{macrocode}
% Ignore bogus options:
%    \begin{macrocode}
      else:
        ignore_option (opt[nopt], opt[nopt]arg);
      fi
    endfor
  endfor
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vvertexn (expr vtxsty) (suffix v) (expr n) =
  vvertex (vtxsty, vmklist (v, n));
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfblob}
%   \begin{macro}{\fmfdot}
% We can decorate vertices with ``blobs'' and dots from \TeX{} with
% the command sequences:
%    \begin{macrocode}
%<style>\def\fmfblob#1#2{\fmfcmd{vblob ((#1),#2);}}
%<style>\def\fmfdot#1{\fmfcmd{vdot (#1);}}
%    \end{macrocode}
%   \end{macro}
% \end{macro}
%
% The vertices in the list |vl| will be drawn with a blob of diameter
% |bd|:
%    \begin{macrocode}
%<*base>
vardef vblob (expr bd) (text vl)=
  forsuffixes $=vl:
    if not vexists $: venter $; fi
    vlist[vlookup $]decor.shape := fullcircle;
    vlist[vlookup $]decor.size := bd;
    vlist[vlookup $]decor.sty := .5;
 endfor
enddef;
%    \end{macrocode}
%
% The vertices in the list |vl| will be drawn with a dot.
%    \begin{macrocode}
vardef vdot (text vl)=
  forsuffixes $=vl:
    if not vexists $: venter $; fi
    vlist[vlookup $]decor.shape := fullcircle;
    vlist[vlookup $]decor.size := dot_size;
    vlist[vlookup $]decor.sty := 1;
 endfor
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vdotn (suffix v) (expr n) =
  vdot (vmklist (v, n));
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vblobn (suffix v) (expr n) =
  vblob (vmklist (v, n));
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfdotn}
% Place |#2| blobs or dots at $|v|_1,\ldots,|v|_{|#1|}$.
%    \begin{macrocode}
%<style>\def\fmfblobn#1#2{\fmfcmd{vblobn (#1, #2);}}
%<style>\def\fmfdotn#1#2{\fmfcmd{vdotn (#1, #2);}}
%    \end{macrocode}
% \end{macro}
%
% \begin{macro}{\fmfleft}
%   \begin{macro}{\fmfright}
%     \begin{macro}{\fmfbottom}
%       \begin{macro}{\fmftop}
%         \begin{macro}{\fmfsurround}
% External vertices are positioned thusly in \TeX{}:
% \changes{1.9}{1994/10/27}{%
%   Make \texttt{fmfincoming} and \texttt{fmfoutgoing} obsolescent.
%   Provide \texttt{fmfleft}, \texttt{fmfright}, \texttt{fmfbottom}
%   and \texttt{fmftop} instead.}
% \changes{1.9}{1994/12/29}{Fix typos in \texttt{fmfbottom}
%   and \texttt{fmftop}.}
%    \begin{macrocode}
%<*style>
\def\fmfleft#1{\fmfcmd{vleft(#1);}}
\def\fmfright#1{\fmfcmd{vright(#1);}}
\def\fmfbottom#1{\fmfcmd{vbottom(#1);}}
\def\fmftop#1{\fmfcmd{vtop(#1);}}
\let\fmfincoming\fmfleft
\let\fmfoutgoing\fmfright
\def\fmfsurround#1{\fmfcmd{vsurround(#1);}}
%</style>
%    \end{macrocode}
%         \end{macro}
%       \end{macro}
%     \end{macro}
%   \end{macro}
% \end{macro}
% Here are the ``galleries'' we're hooking our external vertices on
% (see also the pictures on page~\pageref{p:galleries}):
%    \begin{macrocode}
%<*base>
vardef left_gallery = (.1w,0)..(0,.5h)..(.1w,h) enddef;
vardef right_gallery = (.9w,0)..(w,.5h)..(.9w,h) enddef;
vardef bottom_gallery = (0,.1h)..(.5w,0)..(w,.1h) enddef;
vardef top_gallery = (0,.9h)..(.5w,h)..(w,.9h) enddef;
vardef surround_gallery =
  superellipse ((w,.5h), (.5w,h), (0,.5h), (.5w,0), .75)
enddef;
%    \end{macrocode}
% and the \MF{} code which does the hard work for the above
% \TeX{} macros
%    \begin{macrocode}
vardef vleft (text vl) = vdistribute (left_gallery, vl) enddef;
vardef vright (text vl) = vdistribute (right_gallery, vl) enddef;
vardef vbottom (text vl) = vdistribute (bottom_gallery, vl) enddef;
vardef vtop (text vl) = vdistribute (top_gallery, vl) enddef;
vardef vsurround (text vl) = vdistribute (surround_gallery, vl) enddef;
%    \end{macrocode}
%
% Distribute the vertices in the list |vl| evenly along the path |p|:
%    \begin{macrocode}
vardef vdistribute (expr p) (text vl) =
  save numv, len, off;
  numeric numv, len, off;
  numv = count (vl);
%    \end{macrocode}
% If the path is cyclic, place the first vertex twice:
%    \begin{macrocode}
  if cycle p: numv := numv + 1; fi
  len := length (p);
  if numv = 1:
    vforce (point len/2 of p, vl);
  else:
    off := 0;
    forsuffixes $ = vl:
      vforce (point off of p, $);
      off := off + len/(numv-1);
    endfor
  fi
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfleftn}
%   \begin{macro}{\fmfrightn}
%     \begin{macro}{\fmfbottomn}
%       \begin{macro}{\fmftopn}
%         \begin{macro}{\fmfsurroundn}
% A short cut:
%    \begin{macrocode}
%<*style>
\def\fmfleftn#1#2{\fmfcmd{vleftn(#1,#2);}}
\def\fmfrightn#1#2{\fmfcmd{vrightn(#1,#2);}}
\def\fmfbottomn#1#2{\fmfcmd{vbottomn(#1,#2);}}
\def\fmftopn#1#2{\fmfcmd{vtopn(#1,#2);}}
\let\fmfincomingn\fmfleftn
\let\fmfoutgoingn\fmfrightn
\def\fmfsurroundn#1#2{\fmfcmd{vsurroundn(#1,#2);}}
%</style>
%    \end{macrocode}
%         \end{macro}
%       \end{macro}
%     \end{macro}
%   \end{macro}
% \end{macro}
%
%    \begin{macrocode}
%<*base>
def vmklist (suffix v) (expr n) =
  for $ = 1 upto n-1: v[$], endfor v[n]
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vleftn (suffix v) (expr n) =
  vleft (vmklist (v, n));
enddef;
vardef vrightn (suffix v) (expr n) =
  vright (vmklist (v, n));
enddef;
vardef vbottomn (suffix v) (expr n) =
  vbottom (vmklist (v, n));
enddef;
vardef vtopn (suffix v) (expr n) =
  vtop (vmklist (v, n));
enddef;
vardef vsurroundn (suffix v) (expr n) =
  vsurround (vmklist (v, n));
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmffor}
%   \begin{macro}{\endfmffor}
%    \begin{macrocode}
%<*style>
\def\fmffor#1#2#3#4{\fmfcmd{for #1 = #2 step #3 until #4:}}
\def\endfmffor{\fmfcmd{endfor}}
%</style>
%    \end{macrocode}
%   \end{macro}
% \end{macro}
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Choosing a Layout for the Graph}
%
% The procedure |vposition| is called near the end and
% chooses ``optimal'' vertex positions by minimizing the sum of the
% weighted lengths of the arcs.  Since the quantity to be optimized is
% quadratic in the vertices
% \begin{equation}
%   L = \frac{1}{2} \sum_i \sum_{j\in\alpha(i)}
%         t_{ij} (\vec v_i - \vec v_j)^2\,,
% \end{equation}
% where~$\alpha(i)$ denotes the set of vertices connectes with the
% vertex~$i$, we just have to solve a system of linear equations.
% Adding Lagrange multipliers~$\lambda_{ij}$ for the constraints that
% have been specified
% \begin{equation}
%   \Lambda = \sum_i \sum_{j\in\gamma(i) \atop j>i}
%         \vec\lambda_{ij}\cdot(\vec v_i - \vec v_j - \vec d_{ij})\,,
% \end{equation}
% where~$\gamma(i)$ denotes the set of vertices which have a fixed
% distance to the vertex~$i$, the set of linear equations is given by
% \begin{eqnarray}
%   0 & = & \frac{\partial}{\partial \vec v_i} (L+\Lambda)
%            = \sum_{j\in\alpha(i)} t_{ij} (\vec v_i - \vec v_j)
%              + \sum_{j\in\gamma(i) \atop j>i} \vec\lambda_{ij}
%              - \sum_{j\in\gamma(i) \atop j<i} \vec\lambda_{ji} \\
%   0 & = & \vec v_i - \vec v_j - \vec d_{ij}\;\; \mid  j \in \gamma(i)\,.
% \end{eqnarray}
% The implementation is simple: loop over all vertices in |vlist[]|
%    \begin{macrocode}
%<*base>
vardef vposition =
  for i = vertices:
%    \end{macrocode}
% and iff the position of the vertex has not been fixed yet, add
% another equation.  Note that each arc enters twice (incoming
% \emph{and} outgoing) in this procedure.  Thus it is easiest to store
% them \emph{both} ways in the |vlist| structure
% (cf.~page~\pageref{pg:vconnect})\label{pg:vposition}.
%    \begin{macrocode}
    if unknown vlist[i]loc:
      origin = origin
      for j = varcs (i):
        + vlist[i]arc[j]tns * (vlist[i]loc - vlist[vlist[i]arc[j]]loc)
      endfor
      for j = vconstr (i):
        if i < vlist[i]constr[j]:
          + lambda[i][vlist[i]constr[j]]
        else:
          - lambda[vlist[i]constr[j]][i]
        fi
      endfor;
    fi
  endfor
%    \end{macrocode}
% Inquiring minds might want to see the result in numbers:
%    \begin{macrocode}
  if vtracing: vdump; fi
enddef;
%</base>
%    \end{macrocode}
% \begin{macro}{\fmfposition}
% Again, we can ask for positioning and drawing explicitely from \TeX
% (usually called implicitely by |\end{fmfchar}|).  This is useful for
% subsequent fine tuning.
%    \begin{macrocode}
%<style>\def\fmfposition{\fmfcmd{vposition;}}
%    \end{macrocode}
% \end{macro}
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Drawing the Graph}
%
% \begin{macro}{\fmfdraw}
%    \begin{macrocode}
%<style>\def\fmfdraw{\fmfcmd{vdraw;}}
%    \end{macrocode}
% \end{macro}
%
% And here's the actual \MF{} implementation of |vdraw|:
%    \begin{macrocode}
%<*base>
vardef vdraw =
%    \end{macrocode}
% Check that all vertices are known before attempting to draw the
% diagram.
%    \begin{macrocode}
  for i = vertices:
    if not known vlist[i]loc:
      errhelp "Your graph specification was not complete (probably a "
            & "lone vertex).            Check logic and reprocess!";
      errmessage "feynmf: vertex `" & vlist[i]name & "' not determined, "
               & "replaced by `(0,0)'."; 
      vlist[i]loc := origin;
    fi
    if unknown vlist[i]decor.size:
      vlist[i]decor.size = decor_size;
    fi
  endfor
%    \end{macrocode}
% Now do the actual drawing, looping over vertices and arcs.
%    \begin{macrocode}
  for i = vertices:
    for j = varcs (i):
      if known vlist[i]arc[j]sty:
%    \end{macrocode}
% \changes{1.5}{1994/10/20}{Implement optional argument for detours.}
%    \begin{macrocode}
        vdraw_arc (vlist[i]arc[j]sty,
                   cut_decors (vlist[i],
                               vbuild_arc (vlist[i]arc[j]lsr,
                                           vlist[i]loc,
                                           vlist[vlist[i]arc[j]]loc),
                               vlist[vlist[i]arc[j]]),
                   vlist[i]arc[j]lbl);
      fi
    endfor;
    vdraw_vertex_label vlist[i];
    vdraw_vertex vlist[i];
  endfor
enddef;
%    \end{macrocode}
% Construct an arc from |from| to |to|.  The arc will be straight if
% $|lsr| = 0$, a left (approximate) halfcircle if $|lsr| = -1$ and a
% right halfcircle if $|lsr| = 1$.  Othe values of |lsr| will give
% obvious interpolations.  We optimize the most frequent straight
% line case. 
% \changes{1.6}{1994/10/22}{%
%   Don't use \texttt{interpath} and halfcircles for detours anymore.
%   Simple paths constructed from three points are better (and
%   simpler).}
%    \begin{macrocode}
vardef vbuild_arc (expr lsr, from, to) =
  if lsr = 0:
    from -- to
  else:
    from
      .. (1-lsr)/2 *(to rotatedabout (.5[from,to], 90))
         + (1+lsr)/2 * (to rotatedabout (.5[from,to], -90))
      .. to
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vdraw_arc (expr sty, arc) (suffix lbl) =
  scantokens ("draw_" & sty) (arc);
  vdraw_arc_label (arc, lbl);
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vdraw_arc_label (expr arc) (suffix lbl) =
  if lbl <> "":
    save _a, _z, _zz, _r;
    numeric _a;
    pair _z, _zz, _r;
    _z := point .5 length (arc) of arc;
    _r := direction .5 length (arc) of arc rotated - 90;
    if lbl.side = "left":
      _a := angle (-_r);
    elseif lbl.side = "right":
      _a := angle (_r);
    else:
%    \end{macrocode}
% Normalize to avoid overflow in |dotprod|:
% \changes{1.9}{1995/02/18}{%
%   \texttt{vdraw\_arc\_label}: Protect against divide by zero.}
%    \begin{macrocode}
      _zz = _z - .5[point 0 of arc, point infinity of arc];
      if ((_zz if length (_zz) >  0: / length (_zz) fi)
          dotprod _r) >= 0:
        _a := angle (_r);
      else:
        _a := angle (-_r);
      fi
    fi
    LaTeX_text (_z + lbl.dist * thick * dir _a, _a, lbl);
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vdraw_vertex_label suffix v =
  if v.lbl <> "":
    save a;
    numeric a;
    if unknown v.lbl.ang:
      if v.loc = (.5w,.5h):
        a := 0;
      else:
        a := angle (v.loc - (.5w,.5h));
      fi
    else:
      a := v.lbl.ang;
    fi
    LaTeX_text (v.loc + v.lbl.dist * thick * dir a, a, v.lbl);
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vdraw_vertex suffix v =
  save cmd;
  string cmd;
  if known v.decor.shape:
    cmd := "filldraw";
    if known v.decor.sty:
      if v.decor.sty = 0:
        cmd := "draw";
      elseif abs (v.decor.sty) >= 1:
        cmd := "filldraw";
      elseif v.decor.sty > 0:
        cmd := "shadedraw";
      else:
        cmd := "hatchdraw";
      fi
    fi
    scantokens (cmd) v.decor.shape
      if known v.decor.ang: rotated v.decor.ang fi
      scaled v.decor.size shifted v.loc;
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef polygon expr n =
  if n > 2:
    for i = 1 upto n:
      (.5up rotated (360i/n)) --
    endfor
    cycle
  else:
    fullcircle
  fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef polygram expr n =
  if n > 2:
    for i = 1 upto n:
      (.5up rotated (360i/n)) --
      (.2up rotated (360(i+.5)/n)) --
    endfor
    cycle
  else:
    fullcircle
  fi
enddef;
%    \end{macrocode}
%
% Unfortunately, enclosing the |message| in a |batchmode|
% |errorstopmode| pair doesn't work.  The label information isn't
% written to the terminal, but an empty line is anyway \ldots
% \changes{1.4}{1994/05/28}{%
%   \MP: \texttt{write} the label files directly.}
%    \begin{macrocode}
vardef LaTeX expr text =
%<*!mp>
  message (":" & jobname & "." & decimal charcode & ":" & text & "%%%")
%</!mp>
%<*mp>
  if LaTeX_file = "":
    LaTeX_file := jobname & ".t" & decimal charcode;
    write ("% " & LaTeX_file & " -- generated from " & jobname & ".mp")
      to LaTeX_file;
  fi
  write (text & "%%%") to LaTeX_file
%</mp>
enddef;
vardef LaTeX_text (expr z, a, txt) =
  LaTeX "\fmfL(" & (decimal (xpart z/LaTeX_unitlength)) & ","
      & (decimal (ypart z/LaTeX_unitlength)) & ","
      & (voctant a) & "){" & txt & "}";
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfL}
% This is an internal macro for squeezing more text into \MF's
% 80 character wide output.
%    \begin{macrocode}
%<style>\def\fmfL(#1,#2,#3)#4{\put(#1,#2){\makebox(0,0)[#3]{#4}}}
%    \end{macrocode}
% \end{macro}
%
% This will only be used with $\vert|a|\vert\le180$:
%    \begin{macrocode}
%<*base>
vardef voctant expr a =
  voctant_list[floor (a/45 + .5)]
enddef;
string voctant_list[];
voctant_list[-4] := "r";
voctant_list[-3] := "rt";
voctant_list[-2] := "t";
voctant_list[-1] := "lt";
voctant_list[0] := "l";
voctant_list[1] := "lb";
voctant_list[2] := "b";
voctant_list[3] := "rb";
voctant_list[4] := "r";
%    \end{macrocode}
%
%    \begin{macrocode}
vardef vdump =
  message ">>>>> Vertices and arcs for diagram #" & decimal charcode
        & " of " & jobname & ".mf:";
  for i = vertices:
    message "> " & vlist[i]name & "=" & decimal_pair (vlist[i]loc)
          & ": #lines="
          & decimal (vlist[i]arc.last - vlist[i]arc.first + 1)
          if vlist[i]lbl <> "":
            & ", lbl=" & vlist[i]lbl
            & ", l.angle=" & decimal_ (vlist[i]lbl.ang)
            & ", l.dist=" & decimal_ (vlist[i]lbl.dist)
          fi
          & ".";
  endfor
  for i = vertices:
    for j = varcs (i):
      if known vlist[i]arc[j]sty:
        message "> " & vlist[i]name & "*" & vlist[vlist[i]arc[j]]name
                & ": " & vlist[i]arc[j]sty
                & ", tns=" & decimal_ (vlist[i]arc[j]tns)
                & ", lsr=" & decimal_ (vlist[i]arc[j]lsr)
                if vlist[i]arc[j]lbl <> "":
                  & ", lbl=" & vlist[i]arc[j]lbl
                  & ", l.side=" & vlist[i]arc[j]lbl.side
                  & ", l.dist=" & decimal_ (vlist[i]arc[j]lbl.dist)
                fi
                & ".";
      fi
    endfor
    for j = vconstr (i):
      if i < vlist[i]constr[j]:
%    \end{macrocode}
% We don't keep an explicit record of the fixed distances, but they're
% easy to recover:
%    \begin{macrocode}
        save z;
        pair z;
        z = vlist[vlist[i]constr[j]]loc - vlist[i]loc;
        message "> " & vlist[i]name & "&"
                & vlist[vlist[i]constr[j]]name
                & ": " & decimal_pair (z);
      fi
    endfor;
  endfor
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef decimal_ (text n) =
  if known n: decimal n else: "?" fi
enddef;
%    \end{macrocode}
%
%    \begin{macrocode}
vardef decimal_pair (text z) =
  "(" & decimal_ (xpart z) & "," & decimal_ (ypart z) & ")"
enddef;
%    \end{macrocode}
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \subsubsection{Online displays}
%
% This is a bit smarter about pictures of varying sizes and some
% overshooting than |showit|.  You can still get burned, though,
% because \MF{} might not be able to enlarge the screen sufficiently.
% \changes{1.9}{1994/10/25}{Online display support.}
%    \begin{macrocode}
def show_diagram_ expr frame =
  if (screen_cols < w + 2 xpart frame) or (screen_rows < h + 2 ypart frame):
    screen_cols := w + 2 xpart frame;
    screen_rows := h + 2 ypart frame;
    openwindow currentwindow
      from origin to (screen_rows, screen_cols)
      at (- xpart frame, h + ypart frame);
  fi
  showit_;
  if showstopping > 0:
    stop "This is diagram #" & decimal charcode
       & ".  Hit return to continue...";
  fi
enddef;
%    \end{macrocode}
% Self-modifying code is \emph{fun}: make sure to clear the window the
% second time around.
%    \begin{macrocode}
def show_diagram =
  def show_diagram =
    display blankpicture inwindow currentwindow;
    show_diagram_
  enddef;
  show_diagram_
enddef;
%    \end{macrocode}
% |show_all_diagrams| turns on the above online display mechanism.
% Creative use of |extra_endchar| allows us to do this from the
% command line (|showstopping| is used here to slow down the slide
% show).
% \begin{verbatim}
% mf '\mode:=localmode;
%     showstopping:=1;
%     extra_endchar:="show_all_diagrams(100,100);";
%     input foo.mf'
% \end{verbatim}
%    \begin{macrocode}
def show_all_diagrams expr frame =
  def showit = show_diagram frame enddef;
  displaying:=1;
enddef;
%</base>
%    \end{macrocode}
%
% \begin{macro}{\fmfdisplay}
% Make the display accessible from \TeX{} too.
%    \begin{macrocode}
%<*style>
\def\fmfdisplay{\fmfcmd{show_all_diagrams (100,100);}}
\def\fmfstopdisplay{\fmfcmd{showstopping:=1;}\fmfdisplay}
%</style>
%    \end{macrocode}
% \end{macro}
%
% Now we're done with the \MF{} macros
%    \begin{macrocode}
%<*base>
endinput;
%</base>
%    \end{macrocode}
% and the \TeX{} macros too:
%    \begin{macrocode}
%<*style>
\mdqrestore
%</style>
%    \end{macrocode}
%
% \Finale
%
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \appendix
% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% \section{Driver file}
%
%    \begin{macrocode}
%<*driver>
%<*!209>
\documentclass[a4paper]{article}
\usepackage{doc}
%    \end{macrocode}
% The \MF{} and \MP{} logos come out much nicer if you have |mflogo|
% installed:
%    \begin{macrocode}
\IfFileExists{mflogo.sty}%
  {\usepackage{mflogo}%
   \def\FMF{\texttt{feyn}\textlogo{MF}}}%
  {\def\MF{\textsf{META}\-\textsf{FONT}}%
   \def\MP{\textsf{META}\-\textsf{POST}}%
   \def\FMF{\texttt{feyn}\textsf{MF}}}
%    \end{macrocode}
% Here is the place to declare your own PostScript aware |dvi| driver
% option:
%    \begin{macrocode}
%<mp>\usepackage[dvips]{feynmp}
%<!mp>\usepackage{feynmf}
%</!209>
%<*209>
%<mp>\documentstyle[doc,feynmp209]{article}
%<!mp>\documentstyle[doc,feynmf209]{article}
\def\textit#1{{\it#1\/}}
\def\textbf#1{{\bf#1}}
\def\textsf#1{{\sf#1}}
\def\texttt#1{{\tt#1}}
\def\emph#1{{\em#1\/}}
\let\bfseries\bf
\def\LaTeXe{\LaTeX$2_\epsilon$}
\def\MF{\textsf{META}\-\textsf{FONT}}
\def\MP{\textsf{META}\-\textsf{POST}}
\def\FMF{\texttt{feyn}\textsf{MF}}
%</209>
\font\manfnt=manfnt
\def\dangerousbend/{{\manfnt\char"7F}}
\def\dubious{\begin{itemize}\item[\dangerousbend/]}
\def\enddubious{\end{itemize}}
\parindent0pt
%<manual>\OnlyDescription
\EnableCrossrefs
\RecordChanges
\CodelineIndex
\DoNotIndex{\def,\gdef,\long,\let,\begin,\end,\if,\ifx,\else,\fi}
\DoNotIndex{\immediate,\write,\newwrite,\openout,\closeout,\typeout}
\DoNotIndex{\font,\nullfont,\jobname,\documentclass}
\DoNotIndex{\batchmode,\errorstopmode,\char,\catcode,\ }
\DoNotIndex{\CodelineIndex,\docdate,\DocInput,\DoNotIndex,\EnableCrossrefs}
\DoNotIndex{\filedate,\filename,\fileversion,\logo,\manfnt}
\DoNotIndex{\NeedsTeXFormat,\ProvidesPackage,\RecordChanges,\space}
\DoNotIndex{\usepackage,\wlog,\@gobble,\@ifundefined,\@namedef,\@spaces}
\DoNotIndex{\begingroup,\csname,\edef,\endcsname,\expandafter,\hbox}
\DoNotIndex{\hskip,\ifeof,\ignorespaces,\item,\leavevmode,\loop,\makebox}
\DoNotIndex{\newcounter,\newif,\newread,\openin,\par,\parindent,\put}
\DoNotIndex{\read,\relax,\repeat,\setcounter,\stepcounter,\the}
\DoNotIndex{\value,\vbox,\vskip}
\DoNotIndex{}
%    \end{macrocode}
% Cut the linebreaking some slack for macrocode which might conatin
% long lines (it doesn't really hurt if they stick out a bit).
%    \begin{macrocode}
\let\origmacrocode\macrocode
\def\macrocode{\hfuzz 5em\origmacrocode}
\begin{document}
  \DocInput{feynmf.dtx}
\end{document}
%</driver>
%    \end{macrocode}
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\endinput
Local Variables:
mode:LaTeX
fill-prefix:"% "
indent-tabs-mode:nil
change-log-default-name:"TODO"
page-delimiter:"^% %%%%%%%%%*\n"
End:
